【问题标题】:file_get_contents returns 403 forbiddenfile_get_contents 返回 403 禁止
【发布时间】:2011-05-31 13:18:57
【问题描述】:

我正在尝试制作网站爬虫。我在我的本地机器上做了它,它在那里工作得很好。当我在我的服务器上执行相同的操作时,它会显示 403 禁止错误。 我正在使用PHP Simple HTML DOM Parser。我在服务器上遇到的错误是这样的:

警告: file_get_contents(http://example.com/viewProperty.html?id=7715888) [function.file-get-contents]:失败 打开流:HTTP 请求失败! HTTP/1.1 403 禁止在 /home/scraping/simple_html_dom.php 上 第 40 行

触发它的代码行是:

$url="http://www.example.com/viewProperty.html?id=".$id;

$html=file_get_html($url);

我已经检查了服务器上的 php.ini,并且 allow_url_fopen 已打开。可能的解决方案是使用 curl,但我需要知道我哪里出错了。

【问题讨论】:

  • 服务器是你的吗?如果是这样,您或您的托管服务似乎已配置安全设置以防止被废弃。
  • 它不是“我的”服务器,而是专用服务器。
  • 我误读了这个问题。我以为你在报废自己的网站(即,你有明确许可的网站)。 @Pekka 说得对。
  • 投票结束过于广泛。如果服务器返回 403,则表示请求被禁止。如果不是您的服务器,则无法知道除此之外的任何内容。

标签: php curl


【解决方案1】:

我知道这是一个相当古老的线程,但我想分享一些想法。

如果您在访问网页时没有获得任何内容,很可能是它不希望您能够获得该内容。那么它如何识别脚本正在尝试访问网页,而不是人呢?一般是发给服务器的HTTP请求中的User-Agent标头。

所以要让网站认为访问网页的脚本也是一个人类,你必须在请求期间更改User-Agent 标头。如果您将 User-Agent 标头设置为某些常见 Web 浏览器使用的值,大多数 Web 服务器可能会允许您的请求。

浏览器常用的用户代理列表如下:

  • 铬:'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/50.0.2661.102 Safari/537.36'

  • 火狐:Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:75.0) Gecko/20100101 Firefox/75.0

  • 等等……


$context = stream_context_create(
    array(
        "http" => array(
            "header" => "User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/50.0.2661.102 Safari/537.36"
        )
    )
);

echo file_get_contents("www.google.com", false, $context);

这段代码伪造了用户代理并将请求发送到https://google.com

参考资料:

干杯!

【讨论】:

  • "header" => "User-Agent: <signature>""user_agent" => "<signature>" would do
【解决方案2】:

这不是您的脚本的问题,而是您请求的资源的问题。 Web 服务器正在返回“禁止”状态代码。

可能是它阻止了 PHP 脚本以防止抓取,或者如果您发出了太多请求,它可能会阻止您的 IP。

您可能应该与远程服务器的管理员交谈。

【讨论】:

  • 但同时,它在我的本地主机上运行良好。问题似乎与我的服务器配置有关。
  • @absk 不,403 forbidden 显然来自远程服务器。连接工作正常 - 尝试使用不同的 IP 进行验证。可能是您的服务器的 IP 在远程服务器端被阻止
【解决方案3】:

在包含 simple_html_dom.php 后添加它

ini_set('user_agent', 'My-Application/2.5');

【讨论】:

    【解决方案4】:

    您可以在解析器类中从第 35 行开始更改它。

    function curl_get_contents($url)
    {
      $ch = curl_init();
      curl_setopt($ch, CURLOPT_URL, $url);
      curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
      curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 1);
      $data = curl_exec($ch);
      curl_close($ch);
      return $data;
    }
    
    function file_get_html()
    {
      $dom = new simple_html_dom;
      $args = func_get_args();
      $dom->load(call_user_func_array('curl_get_contents', $args), true);
      return $dom;
    }
    

    你试过其他网站吗?

    【讨论】:

    • 但这应该如何修复远程 403?
    • 他提到了cURL,所以答案的第一部分是针对那个,第二部分是“你试过其他网站吗?”,或者他可能会给我们一个链接来检查。我知道 403 是远程的,这就是为什么我建议他在其他网站上尝试。
    • 所以它从其他站点获取数据。看来我的IP刚刚被列入黑名单。有什么办法吗?
    • 您可以购买另一个 IP,或从共享主机中抓取数据以使其不那么明显,但它们也可以阻止其他 IP。首先从其他服务器尝试,并在您抓取时暂停以看起来更像普通用户。
    【解决方案5】:

    似乎远程服务器有某种类型的阻塞。可能是 user-agent,如果是这种情况,您可以尝试使用 curl 来模拟 Web 浏览器的用户代理,如下所示:

    $url="http://www.example.com/viewProperty.html?id=".$id;
    $ch = curl_init();
    curl_setopt($ch, CURLOPT_URL, $url);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt($ch,CURLOPT_USERAGENT,'Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.13) Gecko/20080311 Firefox/2.0.0.13');
    $html = curl_exec($ch);
    curl_close($ch);
    

    【讨论】:

      【解决方案6】:

      把这个写在 simple_html_dom.php 中对我有用

      function curl_get_contents($url)
      {
        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $url);
      curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
      curl_setopt($ch,CURLOPT_USERAGENT,'Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.13) Gecko/20080311 Firefox/2.0.0.13');
      $html = curl_exec($ch);
        $data = curl_exec($ch);
        curl_close($ch);
        return $data;
      }
      
      function file_get_html($url, $use_include_path = false, $context=null, $offset = -1, $maxLen=-1, $lowercase = true, $forceTagsClosed=true, $target_charset = DEFAULT_TARGET_CHARSET, $stripRN=true, $defaultBRText=DEFAULT_BR_TEXT, $defaultSpanText=DEFAULT_SPAN_TEXT)
      {
          $dom = new simple_html_dom;
        $args = func_get_args();
        $dom->load(call_user_func_array('curl_get_contents', $args), true);
        return $dom;
          //$dom = new simple_html_dom(null, $lowercase, $forceTagsClosed, $target_charset, $stripRN, $defaultBRText, $defaultSpanText);
      
      }
      

      【讨论】:

        【解决方案7】:

        我知道这是一个老问题,但是...

        只需在 linux 上使用 php7 设置我的本地沙箱并遇到此问题。使用终端运行脚本,php 为 CLI 调用 php.ini。我发现“user_agent”选项被注释掉了。我取消了它的注释并添加了一个 Mozilla 用户代理,现在它可以工作了。

        【讨论】:

          【解决方案8】:

          您是否检查了您对文件的权限?我在我的文件上设置了 777(显然是在 localhost 中)并解决了这个问题。

          【讨论】:

            【解决方案9】:

            您可能还需要一些额外的信息,以使网站相信请求来自人。所做的是从浏览器进入网站,复制在 http 请求中发送的任何额外信息。

            $context = stream_context_create(
                    array(
                        "http" => array(
                            'method'=>"GET",
                            "header" => "User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64) 
                                        AppleWebKit/537.36 (KHTML, like Gecko) 
                                        Chrome/50.0.2661.102 Safari/537.36\r\n" .
                                        "accept: text/html,application/xhtml+xml,application/xml;q=0.9,
                                        image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3\r\n" .
                                        "accept-language: es-ES,es;q=0.9,en;q=0.8,it;q=0.7\r\n" . 
                                        "accept-encoding: gzip, deflate, br\r\n"
                        )
                    )
                );
            

            【讨论】:

              【解决方案10】:

              在我的例子中,服务器通过它的 .htaccess 配置拒绝了 HTTP 1.0 协议。 file_get_contents 似乎使用的是 HTTP 1.0 版本。

              【讨论】:

                【解决方案11】:

                使用以下代码: 如果你使用 -> file_get_contents

                $context  = stream_context_create(
                  array(
                    "http" => array(
                      "header" => "User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/50.0.2661.102 Safari/537.36"
                    )
                ));
                

                ========= 如果你使用 curl,

                curl_setopt($curl, CURLOPT_USERAGENT,'User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/50.0.2661.102 Safari/537.36');
                

                【讨论】:

                  猜你喜欢
                  • 2022-06-11
                  • 1970-01-01
                  • 1970-01-01
                  • 2013-08-18
                  • 2013-11-28
                  • 2014-09-03
                  • 1970-01-01
                  • 1970-01-01
                  相关资源
                  最近更新 更多