【问题标题】:file_get_contents ignoring verify_peer=>false?file_get_contents 忽略 verify_peer=>false?
【发布时间】:2013-02-25 21:28:13
【问题描述】:

带有 https 主机的file_get_contents 工作得很好,除了特定的主机(来自某些公司的测试 api 服务器 - ip 白名单,不能给你测试的 URL)。这排除了未加载的 https 模块和其他初始设置错误。

我已经测试了多个 PHP 安装,都在 v5.3.3、32 位、Debian 32 位。

请求适用于 cURL,但前提是设置 curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, 0);。但是,在 file_get_contents 的上下文中设置 verify_peer"=>false 似乎没有任何区别。

使用 file_get_contents,完全相同的请求(相同的 URL,相同的 XML POST 数据)失败,SSL: Connection reset by peer

$arrContextOptions=array(
    "http" => array(
        "method" => "POST",
        "header" => 
            "Content-Type: application/xml; charset=utf-8;\r\n".
            "Connection: close\r\n",
        "ignore_errors" => true,
        "timeout" => (float)30.0,
        "content" => $strRequestXML,
    ),
    "ssl"=>array(
        "allow_self_signed"=>true,
        "verify_peer"=>false,
    ),
);

file_get_contents("https://somedomain:2000/abc/", false, stream_context_create($arrContextOptions));

.

有没有人在使用 file_get_contents 时遇到过这种情况? 有任何调试方法的想法吗?

【问题讨论】:

  • 您是否尝试将allow_self_signed 设置为false?
  • 刚刚试了一下,同样的错误。
  • 为什么不直接使用 cURL?
  • 是的,cURL 似乎是最好的选择。一些谷歌搜索告诉我,其他人也有同样的问题,但无法解决。他们都回到了 cURL。
  • 这个问题很晚,但你也可以试试'verify_peer_name'=>false

标签: php ssl https


【解决方案1】:

你错过了verify_peer_name。如果您也将其设置为 false,则请求有效:

$arrContextOptions=array(
    "http" => array(
        "method" => "POST",
        "header" => 
            "Content-Type: application/xml; charset=utf-8;\r\n".
            "Connection: close\r\n",
        "ignore_errors" => true,
        "timeout" => (float)30.0,
        "content" => $strRequestXML,
    ),
    "ssl"=>array(
        "allow_self_signed"=>true,
        "verify_peer"=>false,
        "verify_peer_name"=>false,
    ),
);

file_get_contents("https://somedomain:2000/abc/", false, stream_context_create($arrContextOptions));

【讨论】:

    【解决方案2】:

    不知道这是否真的有帮助,但请尝试从您的选项数组中删除 SSL 选项。

    这背后的原因: 根据http://www.php.net/manual/en/context.ssl.phpverify_peer默认为false

    allow_self_signed 需要verify_peer,默认为false

    根据上述情况,我推测allow_self_signed 可能会覆盖您对verify_peer 的设置。

    所以请尝试不使用 SSL 或不使用 allow_self_signed 的任何选项,如果有帮助,请告诉我们。

    【讨论】:

      【解决方案3】:

      您可以尝试使用Wireshark 进行调试——您可能会更好地了解问题所在,您应该会看到发生了哪个 SSL 错误。

      【讨论】:

      • 您收到“对等方重置连接”,这意味着它不必挂断。我猜如果客户端和服务器不能就使用哪个 SSL 握手版本达成一致,你会得到这个错误。
      【解决方案4】:

      试试这个代码:

      $fp = fsockopen("ssl://somedomain/abc/", 2000 , $ErrNo, $ErrString, 30);
      if (!$fp) {
          echo "Error No : $ErrNo - $ErrString <br />\n";
      } else {
          $out  = "POST / HTTP/1.1\r\n";
          $out .= "Host: somedomain \r\n";
          $out .= "Content-Type: application/xml; charset=utf-8;\r\n";
          $out .= "Connection: Close\r\n\r\n";
          fwrite($fp, $out);
          while (!feof($fp)) {
              echo fgets($fp, 128);
          }
          fclose($fp);
      }
      

      如果您没有收到错误,我认为问题(使用 file_get_contents)是来自客户端 php 配置,否则来自服务器配置。

      【讨论】:

      • 好的,fsockopen 工作了。但是,PHP 配置没有任何问题。它适用于许多其他 HTTPS 自签名 SSL 证书。
      【解决方案5】:

      只安装这个

      yum install ca-certificates.noarch
      

      【讨论】:

      • 虽然这段代码 sn-p 可以解决问题,但including an explanation 确实有助于提高帖子的质量。请记住,您正在为将来的读者回答问题,而这些人可能不知道您的代码建议的原因。也请尽量不要用解释性 cmets 挤满你的代码,因为这会降低代码和解释的可读性!
      猜你喜欢
      • 2019-11-26
      • 1970-01-01
      • 2011-04-11
      • 2015-11-28
      • 2018-04-23
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多