Bearsampp
2026.7.11
Toggle main menu visibility
Loading...
Searching...
No Matches
class.httpclient.php
Go to the documentation of this file.
1
<?php
2
/*
3
*
4
* * Copyright (c) 2022-2025 Bearsampp
5
* * License: GNU General Public License version 3 or later; see LICENSE.txt
6
* * Website: https://bearsampp.com
7
* * Github: https://github.com/Bearsampp
8
*
9
*/
10
19
class
HttpClient
20
{
28
public
static
function
getHttpHeaders
($pingUrl)
29
{
30
if
(function_exists(
'curl_version'
)) {
31
$result
=
self::getCurlHttpHeaders
($pingUrl);
32
}
else
{
33
$result
=
self::getFopenHttpHeaders
($pingUrl);
34
}
35
36
if
(!empty(
$result
)) {
37
$rebuildResult = array();
38
foreach
(
$result
as $row) {
39
$row = trim($row);
40
if
(!empty($row)) {
41
$rebuildResult[] = $row;
42
}
43
}
44
$result
= $rebuildResult;
45
46
Log::debug
(
'getHttpHeaders:'
);
47
foreach
(
$result
as $header) {
48
Log::debug
(
'-> '
. $header);
49
}
50
}
51
52
return
$result
;
53
}
54
66
public
static
function
getFopenHttpHeaders
($url)
67
{
68
$result
= array();
69
70
$context = stream_context_create(array(
71
'ssl'
=> array(
72
'verify_peer'
=>
false
,
73
'verify_peer_name'
=>
false
,
74
'allow_self_signed'
=>
true
,
75
)
76
));
77
78
$fp = @fopen($url,
'r'
,
false
, $context);
79
if
($fp) {
80
$meta = stream_get_meta_data($fp);
81
$result
= isset($meta[
'wrapper_data'
]) ? $meta[
'wrapper_data'
] :
$result
;
82
fclose($fp);
83
}
84
85
return
$result
;
86
}
87
99
public
static
function
getCurlHttpHeaders
($url)
100
{
101
$result
= array();
102
103
$ch = curl_init();
104
curl_setopt($ch, CURLOPT_RETURNTRANSFER,
true
);
105
curl_setopt($ch, CURLOPT_VERBOSE,
true
);
106
curl_setopt($ch, CURLOPT_HEADER,
true
);
107
curl_setopt($ch, CURLOPT_URL, $url);
108
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER,
false
);
109
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST,
false
);
110
111
$response
= @curl_exec($ch);
112
if
(empty(
$response
)) {
113
return
$result
;
114
}
115
116
Log::trace
(
'getCurlHttpHeaders:'
.
$response
);
117
$responseHeaders = explode(
"\r\n\r\n"
,
$response
, 2);
118
if
(!isset($responseHeaders[0]) || empty($responseHeaders[0])) {
119
return
$result
;
120
}
121
122
return
explode(
"\n"
, $responseHeaders[0]);
123
}
124
134
public
static
function
getWebsiteUrl
($path =
''
, $fragment =
''
, $utmSource =
true
)
135
{
136
global
$bearsamppCore
;
137
138
$url =
APP_WEBSITE
;
139
if
(!empty($path)) {
140
$url .=
'/'
. ltrim($path,
'/'
);
141
}
142
if
($utmSource) {
143
$url = rtrim($url,
'/'
) .
'/?utm_source=bearsampp-'
.
$bearsamppCore
->getAppVersion();
144
}
145
if
(!empty($fragment)) {
146
$url .= $fragment;
147
}
148
149
return
$url;
150
}
151
160
public
static
function
getWebsiteUrlNoUtm
($path =
''
, $fragment =
''
)
161
{
162
return
self::getWebsiteUrl
($path, $fragment,
false
);
163
}
164
172
public
static
function
getChangelogUrl
($utmSource =
true
)
173
{
174
return
self::getWebsiteUrl
(
'doc/changelog'
,
null
, $utmSource);
175
}
176
187
public
static
function
getGithubUrl
($type =
'user'
, $user =
APP_GITHUB_USER
, $repo =
null
, $branch =
null
, $path =
null
) {
188
if
(empty($user) || !is_string($user)) {
189
return
false
;
190
}
191
192
// Encode as URL path segment (not query encoding)
193
$user = rawurlencode($user);
194
195
switch
($type) {
196
case
'user'
:
197
return
"https://github.com/{$user}"
;
198
199
case
'repo'
:
200
if
(empty($repo) || !is_string($repo)) {
201
return
false
;
202
}
203
$repo = rawurlencode($repo);
204
return
"https://github.com/{$user}/{$repo}"
;
205
206
case
'issues'
:
207
if
(empty($repo) || !is_string($repo)) {
208
return
false
;
209
}
210
$repo = rawurlencode($repo);
211
return
"https://github.com/{$user}/{$repo}/issues"
;
212
213
case
'raw'
:
214
if
(empty($repo) || empty($branch) || empty($path) || !is_string($repo) || !is_string($branch) || !is_string($path)) {
215
return
false
;
216
}
217
$repo = rawurlencode($repo);
218
$branch = rawurlencode($branch);
219
220
$path = ltrim($path,
'/'
);
221
$segments = array_map(
'rawurlencode'
, explode(
'/'
, $path));
222
$pathEncoded = implode(
'/'
, $segments);
223
224
return
"https://raw.githubusercontent.com/{$user}/{$repo}/{$branch}/{$pathEncoded}"
;
225
226
default
:
227
return
false
;
228
}
229
}
230
236
public
static
function
getGithubUserUrl
()
237
{
238
return
self::getGithubUrl
(
'user'
,
APP_GITHUB_USER
);
239
}
240
254
public
static
function
getHeaders
($host,
$port
, $ssl =
false
)
255
{
256
$result
= array();
257
$context = stream_context_create(array(
258
'ssl'
=> array(
259
'verify_peer'
=>
false
,
260
'verify_peer_name'
=>
false
,
261
'allow_self_signed'
=>
true
,
262
)
263
));
264
265
$fp = @stream_socket_client(($ssl ?
'ssl://'
:
''
) . $host .
':'
.
$port
, $errno, $errstr, 5, STREAM_CLIENT_CONNECT, $context);
266
if
($fp) {
267
$out = fgets($fp);
268
$result
= explode(PHP_EOL, $out);
269
@fclose($fp);
270
}
271
272
if
(!empty(
$result
)) {
273
$rebuildResult = array();
274
foreach
(
$result
as $row) {
275
$row = trim($row);
276
if
(!empty($row)) {
277
$rebuildResult[] = $row;
278
}
279
}
280
$result
= $rebuildResult;
281
282
Log::debug
(
'getHeaders:'
);
283
foreach
(
$result
as $header) {
284
Log::debug
(
'-> '
. $header);
285
}
286
}
287
288
return
$result
;
289
}
290
298
public
static
function
getApiJson
($url)
299
{
300
$header =
self::setupCurlHeaderWithToken
();
301
302
$ch = curl_init();
303
curl_setopt($ch, CURLOPT_SSLVERSION, CURL_SSLVERSION_TLSv1_2);
304
curl_setopt($ch, CURLOPT_RETURNTRANSFER,
true
);
305
curl_setopt($ch, CURLOPT_VERBOSE,
false
);
// Set to false to avoid polluting logs unless needed
306
curl_setopt($ch, CURLOPT_URL, $url);
307
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER,
false
);
308
curl_setopt($ch, CURLOPT_SSL_VERIFYHOST,
false
);
309
curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
310
$data = curl_exec($ch);
311
if
(curl_errno($ch)) {
312
Log::error
(
'CURL Error ('
. curl_errno($ch) .
'): '
. curl_error($ch) .
' (URL: '
. $url .
')'
);
313
}
314
315
$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
316
if
($httpCode >= 400) {
317
Log::error
(
'HTTP Error '
. $httpCode .
' for URL: '
. $url);
318
}
319
320
// curl_close() is deprecated in PHP 8.5+ as it has no effect since PHP 8.0
321
// The resource is automatically closed when it goes out of scope
322
if
(PHP_VERSION_ID < 80500) {
323
curl_close($ch);
324
}
325
326
return
$data ===
false
?
''
: trim($data);
327
}
328
336
public
static
function
getLatestVersion
($url)
337
{
338
$result
=
self::getApiJson
($url);
339
if
(empty(
$result
)) {
340
Log::error
(
'Cannot retrieve latest github info: empty result or error for URL: '
. $url);
341
342
return
null
;
343
}
344
345
$resultArray = json_decode(
$result
,
true
);
346
if
($resultArray ===
null
) {
347
Log::error
(
'Failed to decode JSON response from: '
. $url .
'. Response snippet: '
. substr(
$result
, 0, 100));
348
return
null
;
349
}
350
351
if
(isset($resultArray[
'tag_name'
]) && isset($resultArray[
'assets'
][0][
'browser_download_url'
])) {
352
$tagName = $resultArray[
'tag_name'
];
353
$downloadUrl = $resultArray[
'assets'
][0][
'browser_download_url'
];
354
$name = $resultArray[
'name'
];
355
Log::debug
(
'Latest version tag name: '
. $tagName);
356
Log::debug
(
'Download URL: '
. $downloadUrl);
357
Log::debug
(
'Name: '
. $name);
358
359
return
[
'version'
=> $tagName,
'html_url'
=> $downloadUrl,
'name'
=> $name];
360
}
else
{
361
Log::error
(
'Tag name, download URL, or name not found in the response: '
.
$result
);
362
363
return
null
;
364
}
365
}
366
372
public
static
function
setupCurlHeaderWithToken
()
373
{
374
// Return headers with User-Agent, which is required by GitHub API
375
return
array(
376
'User-Agent: '
.
APP_GITHUB_USERAGENT
.
' (https://github.com/'
.
APP_GITHUB_USER
.
'/'
.
APP_GITHUB_REPO
.
')'
,
377
'Accept: application/vnd.github.v3+json'
378
);
379
}
380
389
public
static
function
getRemoteFilesize
($url, $humanFileSize =
true
)
390
{
391
$size = 0;
392
393
$data = get_headers($url,
true
);
394
if
(isset($data[
'Content-Length'
])) {
395
$size = intval($data[
'Content-Length'
]);
396
}
397
398
return
$humanFileSize ?
Util::humanFileSize
($size) : $size;
399
}
400
409
public
static
function
checkInternetState
()
410
{
411
$connected = @fsockopen(
'www.google.com'
, 80);
412
if
($connected) {
413
fclose($connected);
414
415
return
true
;
// Internet connection is active
416
}
else
{
417
return
false
;
// Internet connection is not active
418
}
419
}
420
}
421
$result
$result
Definition
ajax.apache.php:19
$port
$port
Definition
ajax.apache.php:34
$response
$response
Definition
ajax.apply.moduleconfig.php:26
$bearsamppCore
global $bearsamppCore
Definition
ajax.latestversion.php:24
HttpClient
Definition
class.httpclient.php:20
HttpClient\getWebsiteUrlNoUtm
static getWebsiteUrlNoUtm($path='', $fragment='')
Definition
class.httpclient.php:160
HttpClient\getRemoteFilesize
static getRemoteFilesize($url, $humanFileSize=true)
Definition
class.httpclient.php:389
HttpClient\getGithubUrl
static getGithubUrl($type='user', $user=APP_GITHUB_USER, $repo=null, $branch=null, $path=null)
Definition
class.httpclient.php:187
HttpClient\getHeaders
static getHeaders($host, $port, $ssl=false)
Definition
class.httpclient.php:254
HttpClient\getHttpHeaders
static getHttpHeaders($pingUrl)
Definition
class.httpclient.php:28
HttpClient\getLatestVersion
static getLatestVersion($url)
Definition
class.httpclient.php:336
HttpClient\getGithubUserUrl
static getGithubUserUrl()
Definition
class.httpclient.php:236
HttpClient\getChangelogUrl
static getChangelogUrl($utmSource=true)
Definition
class.httpclient.php:172
HttpClient\getWebsiteUrl
static getWebsiteUrl($path='', $fragment='', $utmSource=true)
Definition
class.httpclient.php:134
HttpClient\getApiJson
static getApiJson($url)
Definition
class.httpclient.php:298
HttpClient\setupCurlHeaderWithToken
static setupCurlHeaderWithToken()
Definition
class.httpclient.php:372
HttpClient\getFopenHttpHeaders
static getFopenHttpHeaders($url)
Definition
class.httpclient.php:66
HttpClient\getCurlHttpHeaders
static getCurlHttpHeaders($url)
Definition
class.httpclient.php:99
HttpClient\checkInternetState
static checkInternetState()
Definition
class.httpclient.php:409
Log\debug
static debug($data, $file=null)
Definition
class.log.php:616
Log\trace
static trace($data, $file=null)
Definition
class.log.php:605
Log\error
static error($data, $file=null)
Definition
class.log.php:650
Util\humanFileSize
static humanFileSize(int $size, string $unit='')
Definition
class.util.php:979
APP_GITHUB_USERAGENT
const APP_GITHUB_USERAGENT
Definition
root.php:18
APP_WEBSITE
const APP_WEBSITE
Definition
root.php:14
APP_GITHUB_USER
const APP_GITHUB_USER
Definition
root.php:16
APP_GITHUB_REPO
const APP_GITHUB_REPO
Definition
root.php:17
sandbox
core
classes
class.httpclient.php
Generated by
1.17.0