PHP:如何使用 cURL 获取网站并像真正的浏览器一样运行?

Dav*_*vid 4 php apache http server

我想从一个特定的网站获取 PHP cURL 的源代码。

使用我的计算机上的浏览器访问该网站没有任何问题。

但是,当我想使用 PHP 脚本访问该网站时,该网站会识别出这是一个自动请求并显示一条错误消息。

这是我的 PHP 脚本:

<?php
$url = "https://www.example.com";
$user_agent = "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_13_6) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/13.0.1 Safari/605.1.15";
$header = array('http' => array('user_agent' => $user_agent));

$ch = curl_init($url);
curl_setopt($ch, CURLOPT_USERAGENT, $user_agent);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$data = curl_exec($ch);
curl_close($ch);
echo $data;
?>
Run Code Online (Sandbox Code Playgroud)

用户代理与我在浏览器中使用的用户代理相同。我正在使用带有 MAMP PRO 的本地服务器。这意味着我使用相同的 IP 地址进行浏览器访问和 PHP 脚本访问。

我已经尝试过使用许多不同的标头和选项的 PHP 脚本,但没有任何效果。

对于我想要访问网站的 Web 服务器来说,必须有任何东西使 PHP 脚本访问看起来与浏览器访问不同。但什么?你有好主意吗?

编辑

我发现它可以与这个 cURL 一起使用:

curl 'https://www.example.com/' -H 'user-agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_13_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.70 Safari/537.36' -H 'accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3' -H 'accept-language: de-DE,de;q=0.9,en-US;q=0.8,en;q=0.7'
Run Code Online (Sandbox Code Playgroud)

如果我在终端中输入此内容,它会显示正确的源代码。

我将其转换为 PHP 脚本,如下所示:

<?php
$ch = curl_init();

curl_setopt($ch, CURLOPT_URL, 'https://www.example.com/');
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'GET');

$headers = array();
$headers[] = 'User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_13_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.70 Safari/537.36';
$headers[] = 'Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3';
$headers[] = 'Accept-Language: de-DE,de;q=0.9,en-US;q=0.8,en;q=0.7';
curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);

$result = curl_exec($ch);
curl_close($ch);
echo $result;
?>
Run Code Online (Sandbox Code Playgroud)

不幸的是,这样它仍然显示错误消息。

这意味着,对于我想要从中访问网站的 Web 服务器,必须有任何东西使命令行访问看起来与浏览器访问不同。但它是什么?

Gre*_*reg 5

除了它请求的 HTTP 标头以及浏览器在客户端上运行 JavaScript 之外,cURL 请求和浏览器发出的请求没有任何区别。

唯一标识 HTTP 客户端的是它的标头(通常是用户代理字符串),并且由于您已将用户代理设置为与浏览器完全相同,因此必须进行其他检查。

默认情况下,cURL 不发送任何默认Accept标头,而浏览器请求带有此标头的页面以显示浏览器的功能。我希望网络服务器会检查类似的事情。

将 HTTP 请求复制为 cURL

看一下上面的 Chrome 开发者工具的屏幕截图。它允许您将整个请求复制为 cURL 请求,包括从 Chrome 发送的所有标头,以便在终端中进行测试。

尝试完全匹配 PHP 中的所有标头,我确信 Web 服务器将无法将您识别为脚本。