WechatPay.php 4.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131
  1. <?php
  2. // +---------------------------------------------------------------------+
  3. // | NiuCloud | [ WE CAN DO IT JUST NiuCloud ]  |
  4. // +---------------------------------------------------------------------+
  5. // | Copy right 2019-2029 www.niucloud.com  |
  6. // +---------------------------------------------------------------------+
  7. // | Author | NiuCloud <niucloud@outlook.com>  |
  8. // +---------------------------------------------------------------------+
  9. // | Repository | https://github.com/niucloud/framework.git  |
  10. // +---------------------------------------------------------------------+
  11. namespace addon\wechatpay\model;
  12. use app\model\BaseModel;
  13. use WeChatPay\Builder;
  14. use WeChatPay\Crypto\Rsa;
  15. use WeChatPay\Util\PemUtil;
  16. /**
  17. * 微信支付配置
  18. * 版本 1.0.4
  19. */
  20. class WechatPay extends BaseModel
  21. {
  22. /**
  23. * 应用实例
  24. * @var \WeChatPay\BuilderChainable
  25. */
  26. private $app;
  27. /**
  28. * @var 平台证书实例
  29. */
  30. private $plateform_certificate_instance;
  31. /**
  32. * @var 平台证书序列号
  33. */
  34. private $plateform_certificate_serial;
  35. /**
  36. * 微信支付配置
  37. */
  38. private $config;
  39. public function __construct($config)
  40. {
  41. $this->config = $config;
  42. $merchant_certificate_instance = PemUtil::loadCertificate(realpath($config['apiclient_cert']));
  43. // 证书序列号
  44. $merchant_certificate_serial = PemUtil::parseCertificateSerialNo($merchant_certificate_instance);
  45. // 加载平台证书
  46. $this->plateform_certificate_instance = PemUtil::loadCertificate(realpath($config['plateform_cert']));
  47. // 平台证书序列号
  48. $this->plateform_certificate_serial = PemUtil::parseCertificateSerialNo($this->plateform_certificate_instance);
  49. $this->app = Builder::factory([
  50. // 商户号
  51. 'mchid' => $config['mch_id'],
  52. // 商户证书序列号
  53. 'serial' => $merchant_certificate_serial,
  54. // 商户API私钥
  55. 'privateKey' => PemUtil::loadPrivateKey(realpath($config['apiclient_key'])),
  56. 'certs' => [
  57. $this->plateform_certificate_serial => $this->plateform_certificate_instance
  58. ]
  59. ]);
  60. }
  61. /**
  62. * 转账
  63. * @param array $options
  64. */
  65. public function transfer(array $data)
  66. {
  67. $this->app->chain('v3/transfer/batches')
  68. ->postAsync([
  69. 'json' => $data,
  70. 'headers' => [
  71. 'Wechatpay-Serial' => $this->plateform_certificate_serial
  72. ]
  73. ])->then(static function($response) use (&$result) {
  74. $result = json_decode($response->getBody()->getContents(), true);
  75. $result = success(0, '', $result);
  76. })->otherwise(static function ($exception) use (&$result) {
  77. if ($exception instanceof \GuzzleHttp\Exception\RequestException && $exception->hasResponse()) {
  78. $result = json_decode($exception->getResponse()->getBody()->getContents(), true);
  79. $result = error(-1, $result['message'], $result);
  80. } else {
  81. $result = error(-1, $exception->getMessage());
  82. }
  83. })->wait();
  84. return $result;
  85. }
  86. /**
  87. *
  88. * @param string $out_batch_no
  89. * @param string $out_detail_no
  90. * @return array
  91. */
  92. public function transferDetail(string $out_batch_no, string $out_detail_no) : array
  93. {
  94. try {
  95. $resp = $this->app->chain("v3/transfer/batches/out-batch-no/{$out_batch_no}/details/out-detail-no/{$out_detail_no}")
  96. ->get();
  97. $result = json_decode($resp->getBody()->getContents(), true);
  98. return $this->success($result);
  99. } catch (\Exception $e) {
  100. if ($e instanceof \GuzzleHttp\Exception\RequestException && $e->hasResponse()) {
  101. $result = json_decode($e->getResponse()->getBody()->getContents(), true);
  102. return $this->error($result, $result['message']);
  103. } else {
  104. return $this->error([], $e->getMessage());
  105. }
  106. }
  107. }
  108. /**
  109. * 加密数据
  110. * @param string $str
  111. * @return string
  112. */
  113. public function encryptor(string $str){
  114. $publicKey = $this->plateform_certificate_instance;
  115. // 加密方法
  116. $encryptor = function($msg) use ($publicKey) { return Rsa::encrypt($msg, $publicKey); };
  117. return $encryptor($str);
  118. }
  119. }