-
Notifications
You must be signed in to change notification settings - Fork 9
Expand file tree
/
Copy pathHTTP_Link_Checker_Client.php
More file actions
169 lines (137 loc) · 4.39 KB
/
Copy pathHTTP_Link_Checker_Client.php
File metadata and controls
169 lines (137 loc) · 4.39 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
<?php
/**
* Link Checker.
*
* @since 1.2.0
*/
declare(strict_types=1);
namespace WPCOMSpecialProjects\Wayback_Link_Fixer\Wayback_Machine\HTTP_Client;
use Throwable;
use WPCOMSpecialProjects\Wayback_Link_Fixer\Settings\Settings;
use WPCOMSpecialProjects\Wayback_Link_Fixer\Wayback_Machine\Link_Checker_Client;
use WPCOMSpecialProjects\Wayback_Link_Fixer\Wayback_Machine\Exception\Service_Offline_Exception;
use WPCOMSpecialProjects\Wayback_Link_Fixer\Wayback_Machine\Exception\Invalid_Response_Exception;
defined( 'ABSPATH' ) || exit;
/**
* Link Checker.
*/
class HTTP_Link_Checker_Client implements Link_Checker_Client {
/**
* Timeout duration.
*
* @var integer
*/
private $timeout;
/**
* Creates a new instance of the Link Checker.
*/
public function __construct() {
$this->timeout = absint( Settings::get_link_checker_timeout() );
}
/**
* Get final url.
*
* @param string $url The URL to check.
*
* @return string The final URL.
*
* @throws Exception If the service is offline or the response is invalid.
*/
public function get_final_url( string $url ): string {
$response = $this->get_decoded_response( $this->query_url( $url ) );
// Return the location if it exists, otherwise return the original url.
return isset( $response['location'] )
? $response['location'] ?? ''
: $url;
}
/**
* Query URL.
*
* @param string $url The URL to check.
* @param array $additional_params Additional parameters to pass to the service.
*
* @return array|WP_Error The Response.
*/
private function query_url( string $url, array $additional_params = array() ): array {
// Compile the url for the live web check service.
$url_params = array(
'url' => wpcomsp_wayback_link_fixer_normalize_url( $url ),
'impersonate' => 1,
);
$url_params = wp_parse_args( $additional_params, $url_params );
$query_url = add_query_arg(
apply_filters( 'wlf_link_checker_url_params', $url_params ),
apply_filters( 'wlf_link_checker_url_base', 'https://iabot-api.archive.org/livewebcheck' )
);
// Get the response.
$response = wp_remote_get( $query_url, array( 'timeout' => $this->timeout ) );
// If we dont have a valid response, throw exception
if ( is_wp_error( $response ) ) {
throw Service_Offline_Exception::create( esc_attr( $response->get_error_message() ) );
}
return $response;
}
/**
* Get the decoded response.
*
* @param array $response The response.
*
* @return array The decoded response.
*
* @throws Exception If the response is invalid.
*/
private function get_decoded_response( array $response ): array {
// If we dont have a 200 response, service may be offline, throw exception.
if ( 200 !== wp_remote_retrieve_response_code( $response ) ) {
throw Service_Offline_Exception::create( esc_attr( 'Response:' . wp_remote_retrieve_response_code( $response ) ) );
}
// Unpack the body.
$body = wp_remote_retrieve_body( $response );
// If we dont have a valid body, throw exception.
if ( ! is_string( $body ) ) {
throw Invalid_Response_Exception::create();
}
// Decode the body.
$body = json_decode( $body, true );
// If we dont have a valid body, throw exception.
if ( ! is_array( $body ) ) {
throw Invalid_Response_Exception::create();
}
return $body;
}
/**
* Check a link.
*
* @param string $url The URL to check.
* @param array<string, mixed> $additional_params Additional parameters to pass to the service.
*
* @return integer the HTTP status code.
*
* @throws Exception If the service is offline or the response is invalid.
*/
public function check_single( string $url, array $additional_params = array() ): int {
// Get the redirected URL if it exists.
$url = $this->get_final_url( $url );
$response = $this->get_decoded_response( $this->query_url( $url, $additional_params ) );
// If we dont have a status code, throw exception.
if ( ! isset( $response['status'] ) ) {
throw Invalid_Response_Exception::create();
}
$code = sanitize_text_field( $response['status'] );
// If we dont have a valid status code, throw exception.
if ( ! is_numeric( $code ) ) {
throw Invalid_Response_Exception::create();
}
return absint( $code );
}
/**
* Checks if the service is online.
*
* @since 1.3.0
*
* @return boolean
*/
public function is_online(): bool {
return wpcomsp_wayback_link_fixer_is_archive_api_online();
}
}