/**
* 微信支付请求接口(POST)
* @param string $openid openid
* @param string $body 商品简单描述
* @param string $order_sn 订单编号
* @param string $total_fee 金额
* @param string $notify_url 回调地址
* @return json的数据
*/
public function wxpay($openid,$total_fee,$body,$order_sn,$notify_url){
$config = $this->config;
//统一下单参数构造
$unifiedorder = array(
'appid' => $config['appid'],
'mch_id' => $config['mch_id'],
'nonce_str' => self::getNonceStr(),
'body' => $body,
'out_trade_no' => $order_sn,
'total_fee' => $total_fee * 100,
'spbill_create_ip' => self::getip(),
'notify_url' => 'http://'.$_SERVER['HTTP_HOST'].'/notify.php',
'trade_type' => 'JSAPI',
'openid' => $openid
);
$unifiedorder['sign'] = self::makeSign($unifiedorder);
//return $unifiedorder;
//请求数据,统一下单
$xmldata = self::array2xml($unifiedorder);
$url = 'https://api.mch.weixin.qq.com/pay/unifiedorder';
$res = self::curl_post_ssl($url, $xmldata);
Log::record("curl_post_ssl 返回");
Log::record($res);
if(!$res){
return array('status'=>0, 'msg'=>"Can't connect the server" );
}
// 这句file_put_contents是用来查看服务器返回的结果 测试完可以删除了
//file_put_contents('./log.txt',$res,FILE_APPEND);
$content = self::xml2array($res);
if(strval($content['result_code']) == 'FAIL'){
return array('status'=>0, 'msg'=>strval($content['err_code']).':'.strval($content['err_code_des']));
}
if(strval($content['return_code']) == 'FAIL'){
return array('status'=>0, 'msg'=>strval($content['return_msg']));
}
$time = time();
settype($time, "string"); //jsapi支付界面,时间戳必须为字符串格式
$resdata = array(
'appId' => strval($content['appid']),
'nonceStr' => strval($content['nonce_str']),
'package' => 'prepay_id='.strval($content['prepay_id']),
'signType' => 'MD5',
'timeStamp' => $time
);
$resdata['paySign'] = self::makeSign($resdata);
return json_encode($resdata);
}
/**
* 微信支付发起请求
*/
protected function curl_post_ssl($url, $xmldata, $second=30,$aHeader=array()){
$config = $this->config;
$ch = curl_init();
//超时时间
curl_setopt($ch,CURLOPT_TIMEOUT,$second);
curl_setopt($ch,CURLOPT_RETURNTRANSFER, 1);
//这里设置代理,如果有的话
//curl_setopt($ch,CURLOPT_PROXY, '10.206.30.98');
//curl_setopt($ch,CURLOPT_PROXYPORT, 8080);
curl_setopt($ch,CURLOPT_URL,$url);
curl_setopt($ch,CURLOPT_SSL_VERIFYPEER,false);
curl_setopt($ch,CURLOPT_SSL_VERIFYHOST,0);
curl_setopt($ch, CURLOPT_SSLVERSION, 1);
//默认格式为PEM,可以注释
curl_setopt($ch,CURLOPT_SSLCERTTYPE,'PEM');
//curl_setopt($ch,CURLOPT_SSLCERT,$config['api_cert']);
curl_setopt($ch,CURLOPT_SSLCERT, ROOT_PATH.'/public/wxcert/'. 'apiclient_cert.pem');
//默认格式为PEM,可以注释
curl_setopt($ch,CURLOPT_SSLKEYTYPE,'PEM');
//curl_setopt($ch,CURLOPT_SSLKEY,$config['api_key']);
curl_setopt($ch,CURLOPT_SSLKEY,ROOT_PATH.'/public/wxcert/'. 'apiclient_key.pem');
//curl_setopt($ch,CURLOPT_CAINFO,$config['rootca']);
Log::record("call api_cert, api_cert:".$config['api_cert']);
if( count($aHeader) >= 1 ){
curl_setopt($ch, CURLOPT_HTTPHEADER, $aHeader);
}
curl_setopt($ch,CURLOPT_POST, true);
curl_setopt($ch,CURLOPT_POSTFIELDS,$xmldata);
**$data = curl_exec($ch);**
if($data){
curl_close($ch);
return $data;
}else {
$error = curl_errno($ch);
echo "call faild, errorCode:$error\n";
** Log::record("call faild, errorCode:".$error);**//此处返回:58错误代码
curl_close($ch);
return false;
}
}
#根据错误代码查看:
Not used in modern versions
CURLE SSL CERTPROBLEM (58)
problem with the local client certificate.
SSL CURLE CLPHER (59)
各位,这个问题如何解决啊
<?php
require_once('vendor/autoload.php');
use WeChatPay\Builder;
use WeChatPay\Crypto\Rsa;
use WeChatPay\Util\PemUtil;
// 设置参数
// 商户号
$merchantId = '190000****';
// 从本地文件中加载「商户API私钥」,步骤2生成的API私钥文件
$merchantPrivateKeyFilePath = 'file:///path/to/merchant/apiclient_key.pem';
$merchantPrivateKeyInstance = Rsa::from($merchantPrivateKeyFilePath, Rsa::KEY_TYPE_PRIVATE);
// 「商户API证书」的「证书序列号」,步骤2生成的序列号
$merchantCertificateSerial = '3775B6A45ACD588826D15E583A95F5DD********';
//「微信支付平台证书」,步骤3生成的证书
$platformCertificateFilePath = 'file:///path/to/wechatpay/cert.pem';
$platformPublicKeyInstance = Rsa::from($platformCertificateFilePath, Rsa::KEY_TYPE_PUBLIC);
// 从「微信支付平台证书」中获取「证书序列号」,步骤3生成的证书
$platformCertificateSerial = PemUtil::parseCertificateSerialNo($platformCertificateFilePath);
// 构造一个 APIv3 客户端实例
$instance = Builder::factory([
'mchid' => $merchantId,
'serial' => $merchantCertificateSerial,
'privateKey' => $merchantPrivateKeyInstance,
'certs' => [
$platformCertificateSerial => $platformPublicKeyInstance,
],
]);
// 发送请求
$resp = $instance->chain('v3/certificates')->get(
['debug' => true] // 调试模式,https://docs.guzzlephp.org/en/stable/request-options.html#debug
);
echo $resp->getBody(), PHP_EOL;
引用chatGPT作答,这个错误似乎与使用SSLv3或TLSv1协议有关,这些协议在现代PHP版本中被默认禁用,因为它们不再被认为是安全的。错误代码58表示SSL连接无法建立。
为解决此错误,您可以尝试以下步骤:
1.将PHP版本升级到最新的稳定版本。如果您使用的是较旧的PHP版本,则可能不支持较新且更安全的SSL/TLS协议。
2.检查远程服务器是否支持您正在使用的SSL/TLS协议。您可以尝试使用其他协议,如TLSv1.2或TLSv1.3。
3.检查正在使用的SSL证书是否有效且受信任。如果证书已过期或未由受信任的证书颁发机构(CA)颁发,则SSL连接可能失败。
4.在您的PHP配置中启用适当的SSL/TLS协议和密码套件。您可以通过修改php.ini文件中的openssl.cafile和openssl.capath设置来实现此操作。
以下答案由GPT-3.5大模型与博主波罗歌共同编写:
根据代码中的注释,我们可以得知这个问题是在使用curl_exec时发生的。具体来说,根据curl_exec返回的结果是false或者null,这个错误可能与一下几个问题之一有关:
根据代码中的注释,我们可以得知证书的路径是硬编码在代码中的,这可能会导致证书找不到的问题。为了解决这个问题,我们可以尝试更新证书的路径使其与实际路径匹配。
由于我们使用了SSL加密,可能会出现IP/主机名解析问题。为了解决这个问题,您可以尝试在请求之前使用以下代码进行解析:
$ip = gethostbyname($hostname);
其中,$hostname是您要请求的主机名或域名。$ip是您获取到的IP地址。
服务器可能无法连接到您指定的端口。在这种情况下,您可以尝试检查您的端口号是否正确,并确保服务器端口没有被防火墙屏蔽。
由于PHP的编译问题,可能会导致curl_exec无法正常工作。解决这个问题的方法是重新编译PHP并启用CURL。这个问题比较棘手,如果您不知道如何重新编译PHP,请参考PHP官方文档或咨询您的PHP服务提供商。
希望这些解决方案能够帮到您,如果您需要更详细的帮助,可以提供更多的错误信息或相关代码片段。
如果我的回答解决了您的问题,请采纳!