当前位置: 首页 > 知识库问答 >
问题:

将Curl客户端ssl移动到Guzzle

史和泰
2023-03-14

我在使用PHP 5.3和php 5.5的Guzzev3.9.2。

我有以下使用ssl客户端证书的工作curl代码:

$url = "https://example.com/";
$cert_file = '/path/to/certificate.pem';

$ch = curl_init();
$options = array(
  CURLOPT_RETURNTRANSFER => true,
  CURLOPT_FOLLOWLOCATION => true,
  CURLOPT_URL => $url ,
  CURLOPT_SSLCERT => $cert_file ,
);

curl_setopt_array($ch , $options);
$output = curl_exec($ch);

if (!$output) {
  echo "Curl Error : " . curl_error($ch);
}
else {
  echo htmlentities($output);
}

我试图把它移到古兹尔:

require '/var/www/vendor/autoload.php';
use Guzzle\Http\Client;
$client = new Client();
$request = $client->get($url, array('cert' => $cert_file));
$response = $client->send($request);
echo $response . PHP_EOL;
print 'HI' . PHP_EOL;

当我使用curl运行它时,得到了200个响应。当我用口香糖的时候,我得到了403分。

共有3个答案

苍温文
2023-03-14
If you are using private key then you have to use ssl_key option it will not 
work with cert.You can use **cert** options only with client certificate.

出现此错误有三个原因。

  1. 未提供正确的证书路径。因此无法阅读

古兹尔如何设置 ssl 卷曲路径:

>

  • 对文件使用CURLOPT_CAINFO

    $cert_file = '/var/www/stack/25924147/cert/example.pem'; #Use absolute path as relative path will not work
    $client = new Client();
    $client->setDefaultOption('verify',true); #pass it for self-signed certificate
    $client->setSslVerification($cert_file,true,2);  #Last Verify Option states default value is 2. When the verify value is 0, the connection succeeds regardless of the names in the certificate. Use that ability with caution!. When the verify value is 1, curl_easy_setopt will return an error
    try{
        $request = $client->get($url);
        $options = $request->getCurlOptions(); #used to check curl options is set properly.
        var_dump($options); 
        $response = $client->send($request);
        echo $response . PHP_EOL;
        print 'HI' . PHP_EOL;
    }catch( Guzzle\Http\Exception\CurlException $e){
        print_r($e->getResponse());
        echo "\n Curl Error \n";
    }catch(Guzzle\Http\Exception\ClientErrorResponseException $e){
       print_r($e->getResponse());
       echo "\n Response Error \n";
    }catch( Guzzle\Http\Exception\RequestException $e){
      print_r($e->getResponse());
      echo "\n REquest Error \n";
    }
    

    或者,如果您想对每个请求都传递证书,请尝试下面代码

       $cert_file = '/var/www/stack/25924147/cert/example.pem'; #Use absolute path as relative path will not work
       $client = new Client();
       $request = $client->get('https://www.example.com', array(), array(
    
          'ssl_key' => array('/etc/pki/private_key.pem')
    
      )
    
    
    With Passoword - 
     $request = $client->get('https://www.example.com', array(), array(
    
         'ssl_key' => array('/etc/pki/private_key.pem', 's3cr3tp455w0rd')
    
     )
    

    对于咕噜咕噜 http 客户端 文档检查 - 咕噜 HTTP 客户端

  • 郎伟兆
    2023-03-14

    首先,因为这导致了一些混乱,Gihub上有两个版本Guzzle:

    • 咕噜噜3(旧版本,你正在使用)
    • 咕噜咕噜(新的,重写的版本)

    这里有两个(经过测试的工作)示例,每个版本的Guzzes都有一个:

    对于Guzzle的最新版本(不是所谓的旧版本Guzzle3 ),应该是:

    use GuzzleHttp\Client;
    
    $client = new Client();
    $response = $client->get($url, array('cert' => $cert_file));
    
    var_dump($response);
    

    确保客户端证书以PEM格式存储。如果证书受密码保护,则需要这样指定:

    $response = $client->get($url, 
        array('cert' => array($cert_file, 'password' => '****'));
    

    !!注意上面提供密码的代码在手册中有所描述,但在最近的版本中不起作用。

    对于旧版本 Guzzle3 (您正在使用)

    use Guzzle\Http\Client;
    
    // Create a client and provide a base URL
    $client = new Client();
    
    $request = $client->get($url, array(), array(
        'cert' => $cert_file
    ));
    
    // You must send a request in order for the transfer to occur
    $response = $request->send();
    
    var_dump($response);
    
    轩辕翰
    2023-03-14

    试试像这样:

     $client = new Client();
     $response = $client->get($url, array(), array('cert' => $cert_file));
    

    并添加以下行进行检查:

     $this->assertEquals($cert_file, $request->getCurlOptions()->get(CURLOPT_SSLCERT));
    

    或使用此:

     $client = new Client();
     $request = $client->createRequest('GET', $url);
     $request->getCurlOptions()->set(CURLOPT_SSLCERT, $cert_file);
     $response = $client->send($request);
    

    如果使用自签名证书,请设置此选项:

    $request->getCurlOptions()->set(CURLOPT_SSL_VERIFYHOST, false);
    $request->getCurlOptions()->set(CURLOPT_SSL_VERIFYPEER, false);
    

    在发送请求之前设置此行:

    $request = $client->get( .... )
    .
    .
    .
    $request->setResponse(new Response(200), true);
    $request->send();
    

    检查您的url,并像这样输入:

    $url = 'https://example.com/index.php';
    

    您可以添加默认选项,例如curl代码:

    $request->getCurlOptions()->set(CURLOPT_RETURNTRANSFER , true);
    $request->getCurlOptions()->set(CURLOPT_FOLLOWLOCATION , true);
    
     类似资料:
    • Http客户端,基于curl扩展实现。 $curl = new Swoole\Client\CURL(); $curl->get("http://www.qq.com/"); $curl->post("http://www.qq.com/", array( 'a' => 1234, 'b' => 5678, )); 支持get、post、download 3种方法 获取HTT

    • 我刚开始穿春靴。到目前为止我还很享受。我已经开发了一个演示SSL rest web服务器,它可以正确处理相互X.509证书身份验证。使用带有自签名客户端和服务器证书的IE浏览器,我测试了演示rest web服务器是否正常工作--服务器和浏览器都成功地交换和验证了彼此的证书。 我很难找到一个SSL客户机示例来说明如何包含客户机证书并发布HTTPS。谁有一个简单的rest客户机示例来说明如何使用我的s

    • 我所拥有的是一个在Dropwizard之上实现的服务器,它需要接受传入的HTTPS连接,并使用附加的证书来唯一标识客户端。我目前在开发过程中使用所有自签名证书。服务器证书对是使用链根对->中间对->服务器对创建的。服务器的P12是使用中间证书和服务器证书加上服务器私钥的串联来创建的。然后它被添加到一个空的JKS中,并成为服务器的密钥库。 我分别创建了两个客户端证书,一个使用相同的中间对作为基础,另

    • 使用MINA框架编写的移动短信通信程序,支持cmpp3.0,cmpp2.0,包含服务端,客户端。实现了移动短信的所有功能

    • 我正在努力与Netty 4.0.8网络套接字客户端示例和SSL,我似乎无法将数据发送到Netty SSL网络套接字服务器示例。尽管围绕这个问题已经有很多帖子了,(我相信我已经浏览了所有的帖子),最常见的建议是在管道的开头添加一个sslHandler,但它不起作用。握手似乎是成功的,因为它也表明了一个相关的问题在这里。 我记得4.0版的情况也一样。0,但我还是设法让它工作了。然而,当我升级到4.0时

    • 问的很多很杂,完全无八股文,所以记得也不是很清楚了~ 1 自我介绍 2 提到了在快手实习,请问实习期间你觉得印象比较深刻的事情是什么 3 客户端开发与你参加实习之前的看法有什么不同 4 工程开发与自己的项目开发有什么区别 5 我简历上有一个和cpu有关的实验课,深挖和扩展了cpu和内存方面的问题 6 还有一些记不清了,大概都是结合项目问一下开放性的问题 7 手撕 string 转int 力扣原题