فهرست منبع

补充 微信支付V3验签方式支持微信平台公钥

萤火科技 1 سال پیش
والد
کامیت
b5e9d270dd

+ 1 - 4
app/common/library/wechat/payment/PlatformCertDown.php

@@ -101,7 +101,6 @@ class PlatformCertDown
             'base_uri' => (string)($opts['baseuri'] ?? self::DEFAULT_BASE_URI),
         ]);
 
-
         /** @var \GuzzleHttp\HandlerStack $stack */
         $stack = $instance->getDriver()->select(ClientDecoratorInterface::JSON_BASED)->getConfig('handler');
         // The response middle stacks were executed one by one on `FILO` order.
@@ -111,17 +110,15 @@ class PlatformCertDown
             'recorder'
         );
 
-
         $instance->chain('v3/certificates')->getAsync(
 //            ['debug' => true]
         )->otherwise(static function ($exception) {
             if ($exception instanceof RequestException && $exception->hasResponse()) {
                 /** @var ResponseInterface $response */
                 $response = $exception->getResponse();
-                throwError((string)$response->getBody());
+                throwError('平台证书文件获取失败:' . (string)$response->getBody());
             }
             throwError($exception->getMessage());
-
         })->wait();
     }
 

+ 8 - 0
app/common/model/PaymentTemplate.php

@@ -67,6 +67,9 @@ class PaymentTemplate extends BaseModel
                     'appId' => '',
                     'mchId' => '',
                     'apiKey' => '',
+                    'signatureMethod' => 'platformCert',   // 验签方式(platformCert平台证书 publicKey微信支付公钥)
+                    'publicKeyId' => '',
+                    'publicKey' => '',
                     'apiclientCert' => '',
                     'apiclientKey' => '',
                 ],
@@ -76,6 +79,9 @@ class PaymentTemplate extends BaseModel
                     'spApiKey' => '',
                     'subAppId' => '',
                     'subMchId' => '',
+                    'spSignatureMethod' => 'platformCert', // 验签方式(platformCert平台证书 publicKey微信支付公钥)
+                    'spPublicKeyId' => '',
+                    'spPublicKey' => '',
                     'spApiclientCert' => '',
                     'spApiclientKey' => ''
                 ]
@@ -152,11 +158,13 @@ class PaymentTemplate extends BaseModel
     {
         if ($method === PaymentMethodEnum::WECHAT) {
             $config['normal'] = $this->setCertFileNames($config['normal'], $method, [
+                'publicKey',
                 'apiclientCert',
                 'apiclientKey',
                 'platformCert'
             ], $storeId);
             $config['provider'] = $this->setCertFileNames($config['provider'], $method, [
+                'spPublicKey',
                 'spApiclientCert',
                 'spApiclientKey',
                 'platformCert'

+ 30 - 10
app/store/model/PaymentTemplate.php

@@ -53,10 +53,8 @@ class PaymentTemplate extends PaymentTemplateModel
         $data['store_id'] = self::$storeId;
         // 写入证书文件
         $data['config'] = [$data['method'] => $this->certFileName($data['method'], $methodConfig)];
-        // 记录微信支付v3平台证书序号
-        if ($data['method'] === 'wechat' && $data['config']['wechat']['version'] === 'v3') {
-            $data['wechatpay_serial'] = $data['config']['wechat'][$data['config']['wechat']['mchType']]['platformCertSerial'];
-        }
+        // 记录微信支付v3平台证书序号或微信支付公钥ID
+        $data['wechatpay_serial'] = $this->wechatpaySerial($data);
         // 写入到数据库
         return $this->save($data);
     }
@@ -77,14 +75,30 @@ class PaymentTemplate extends PaymentTemplateModel
         $data['config'] = [
             $data['method'] => array_merge($methodConfig, $this->certFileName($data['method'], $methodConfig))
         ];
-        // 记录微信支付v3平台证书序号
-        if ($data['method'] === 'wechat' && $data['config']['wechat']['version'] === 'v3') {
-            $data['wechatpay_serial'] = $data['config']['wechat'][$data['config']['wechat']['mchType']]['platformCertSerial'];
-        }
+        // 记录微信支付v3平台证书序号或微信支付公钥ID
+        $data['wechatpay_serial'] = $this->wechatpaySerial($data);
         // 更新到数据库
         return $this->save($data) !== false;
     }
 
+    /**
+     * 记录微信支付v3平台证书序号或微信支付公钥ID
+     * @param array $data
+     * @return string
+     */
+    private function wechatpaySerial(array $data): string
+    {
+        if ($data['method'] === 'wechat' && $data['config']['wechat']['version'] === 'v3') {
+            $mchType = $data['config']['wechat']['mchType'];
+            $field1 = $mchType == 'normal' ? 'signatureMethod' : 'spSignatureMethod';
+            $field2 = $mchType == 'normal' ? 'publicKeyId' : 'spPublicKeyId';
+            return $data['config']['wechat'][$mchType][$field1] == 'publicKey'
+                ? $data['config']['wechat'][$mchType][$field2]
+                : $data['config']['wechat'][$mchType]['platformCertSerial'];
+        }
+        return '';
+    }
+
     /**
      * 记录证书文件名
      * @param string $method 支付方式类型
@@ -96,15 +110,21 @@ class PaymentTemplate extends PaymentTemplateModel
     {
         if ($method === PaymentMethodEnum::WECHAT) {
             $config['normal'] = $this->saveCertFileNames($config['normal'], $method, [
+                'publicKey',
                 'apiclientCert',
                 'apiclientKey'
             ], 'pem');
             $config['provider'] = $this->saveCertFileNames($config['provider'], $method, [
+                'spPublicKey',
                 'spApiclientCert',
                 'spApiclientKey'
             ], 'pem');
-            // 微信支付v3下载 [微信平台证书]
-            $config['version'] === 'v3' && $this->downloadPlatformCert($config);
+            // 微信支付v3验签方式是平台证书时, 需自动下载平台证书
+            if ($config['version'] === 'v3') {
+                $mchType = $config['mchType'];
+                $field1 = $mchType == 'normal' ? 'signatureMethod' : 'spSignatureMethod';
+                $config[$mchType][$field1] == 'platformCert' && $this->downloadPlatformCert($config);
+            }
         }
         if ($method === PaymentMethodEnum::ALIPAY && $config['signMode'] == 10) {
             $config = $this->saveCertFileNames($config, $method, [