我有一个使用Web服务验证字段的Laravel应用程序,REST调用通过HTTPS通过Guzzle。当我通过浏览器发布表单时,一切都很顺利。当我通过phpunit运行同样的测试时,Guzzle失败了:
exception 'GuzzleHttp\Exception\RequestException' with message 'cURL error 51: SSL: certificate verification failed (result: 5)
我尝试了什么:
1-在Guzzle之前,我使用直线卷曲,这给出了相同的行为。我尝试使用curl_setopt($curl, CURLOPT_CAINFO, '/path/to/cacert.pem');
在代码中明确设置cacert并且什么都不做
2-我尝试(同样的结果)将Guzzle指向带有
的cacert$response = $client->request('GET', $url, [
'auth' => ['user', 'pass'],
'verify' => '/path/to/cacert.pem'
]);
3- phpinfo说Apache正在使用它的本地curl和命令行php使用不同的一个,所以我符号链接到Apache版本,结果相同
4- curl.cainfo和openssl.cainfo都已设置
5- /usr/local/etc/openssl/cert.pem
存在
6-在命令行上将-d openssl.cainfo
传递给phpunit什么都不做
代码:
private function curl_rest_call($url){
// $curl = curl_init() ;
// curl_setopt($curl, CURLOPT_HTTPAUTH, CURLAUTH_BASIC);
// curl_setopt($curl, CURLOPT_USERPWD, "user:pass");
// curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, true);
// curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, 2);
// curl_setopt($curl, CURLOPT_CAINFO, '/path/to/cacert.pem');
// curl_setopt($curl, CURLOPT_URL, $url);
// curl_setopt($curl, CURLOPT_RETURNTRANSFER, 1);
// $rest = curl_exec($curl);
// $httpStatus = curl_getinfo($curl, CURLINFO_HTTP_CODE);
// curl_close($curl);
// $result = json_decode($rest) ;
// $result->status = $httpStatus ;
// return $result ;
$client = new Guzzle();
$response = $client->request('GET', $url, [
'auth' => ['user', 'pass'],
'verify' => '/path/to/cacert.pem'
]);
$result = json_decode($response->getBody()->getContents()) ;
$result->status = $response->getStatusCode() ;
return $result ;
}
测试
public function testSuccessfulSignup(){
$this->visit('/free-software')
->type('test@mail.com', 'mail')
->type('Philip', 'first_name')
->type('Fry', 'last_name')
->select('Freelancer', 'profile')
->type('Other', 'industry')
->select('Canada', 'country')
->type('(514) 278-8666', 'phone_number')
->press('Try Harmony Now!')
->seePageIs('/success');
}
答案 0 :(得分:0)
这就是问题所在。
我从命令行调用phpunit
,因为它不是二进制文件的php脚本,它调用php的默认系统安装,而不是网络服务器使用的位置,因此忽略了cacert指令和php.ini配置。
虽然理论上它不应该完全忽略-d openssl.cainfo
开关和CURL_CA_BUNDLE
环境变量(卷曲使用)
最后,我在PATH
变量上添加了webserver php版本,以便调用phpunit
将加载正确的cacert信息。