Skip to content

Commit 05273a9

Browse files
authored
[core] Make getContents exceptions to be handled correctly and correct exception message (RSS-Bridge#2447)
This commit fixes following issues: 1. 'Unexpected response' error message was returned, even if upstream did not return anything 2. Inability to handle non-20x messages with checking response body
1 parent 2e88955 commit 05273a9

File tree

1 file changed

+75
-14
lines changed

1 file changed

+75
-14
lines changed

lib/contents.php

+75-14
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,75 @@
1111
* @link https://github.com/rss-bridge/rss-bridge
1212
*/
1313

14+
15+
/**
16+
* Exception class to handle all errors, when executing getContents
17+
*/
18+
class GetContentsException extends \Exception {
19+
public function __construct($details, $code = 0, Throwable $previous = null) {
20+
$message = trim($this->getMessageHeading() . "\n$details");
21+
22+
$lastError = error_get_last();
23+
if($lastError !== null)
24+
$message .= "\nLast PHP Error: " . $lastError['message'];
25+
26+
parent::__construct($message, $code, $previous);
27+
}
28+
29+
protected function getMessageHeading() {
30+
return 'Could not get contents';
31+
}
32+
}
33+
34+
/**
35+
* Exception class to handle HTTP responses with Cloudflare challenges
36+
**/
37+
class CloudflareChallengeException extends \Exception {
38+
public function __construct($code = 0, Throwable $previous = null) {
39+
if (!$message) {
40+
$message = <<<EOD
41+
The server responded with a Cloudflare challenge, which is not supported by RSS-Bridge!
42+
If this error persists longer than a week, please consider opening an issue on GitHub!
43+
EOD;
44+
}
45+
46+
parent::__construct($message, $code, $previous);
47+
}
48+
}
49+
50+
/**
51+
* Exception class to handle non-20x HTTP responses
52+
**/
53+
class UnexpectedResponseException extends \GetContentsException {
54+
private $responseCode;
55+
private $responseHeaders;
56+
private $responseBody;
57+
58+
protected function getMessageHeading() {
59+
return 'Unexpected response from upstream';
60+
}
61+
62+
public function __construct($responseBody, $responseHeaders, $responseCode = 500, Throwable $previous = null) {
63+
$this->responseCode = $responseCode;
64+
$this->responseHeaders = $responseHeaders;
65+
$this->responseBody = $responseBody;
66+
67+
parent::__construct('', $responseCode, $previous);
68+
}
69+
70+
public function getResponseCode() {
71+
return $this->responseCode;
72+
}
73+
74+
public function getResponseHeaders() {
75+
return $this->responseHeaders;
76+
}
77+
78+
public function getResponseBody() {
79+
return $this->responseBody();
80+
}
81+
}
82+
1483
/**
1584
* Gets contents from the Internet.
1685
*
@@ -189,22 +258,14 @@ function getContents($url, $header = array(), $opts = array(), $returnHeader = f
189258
break;
190259
default:
191260
if(array_key_exists('Server', $finalHeader) && strpos($finalHeader['Server'], 'cloudflare') !== false) {
192-
returnServerError(<<< EOD
193-
The server responded with a Cloudflare challenge, which is not supported by RSS-Bridge!
194-
If this error persists longer than a week, please consider opening an issue on GitHub!
195-
EOD
196-
);
261+
throw new CloudflareChallengeException($errorCode);
262+
}
263+
264+
if ($curlError || $curlErrno) {
265+
throw new GetContentsException('cURL error: ' . $curlError . ' (' . $curlErrno . ')');
197266
}
198267

199-
$lastError = error_get_last();
200-
if($lastError !== null)
201-
$lastError = $lastError['message'];
202-
returnError(<<<EOD
203-
Unexpected response from upstream.
204-
cUrl error: $curlError ($curlErrno)
205-
PHP error: $lastError
206-
EOD
207-
, $errorCode);
268+
throw new UnexpectedResponseException($retval['content'], $retval['header'], $errorCode);
208269
}
209270

210271
return ($returnHeader === true) ? $retVal : $retVal['content'];

0 commit comments

Comments
 (0)