mirror of
https://github.com/v2board/v2board.git
synced 2024-11-10 09:39:10 +08:00
update: rewrite alipay f2f sdk
This commit is contained in:
parent
bd73c3f03a
commit
36f87bd61f
@ -5,8 +5,6 @@
|
|||||||
*/
|
*/
|
||||||
namespace App\Payments;
|
namespace App\Payments;
|
||||||
|
|
||||||
use Omnipay\Omnipay;
|
|
||||||
|
|
||||||
class AlipayF2F {
|
class AlipayF2F {
|
||||||
public function __construct($config)
|
public function __construct($config)
|
||||||
{
|
{
|
||||||
@ -36,28 +34,25 @@ class AlipayF2F {
|
|||||||
|
|
||||||
public function pay($order)
|
public function pay($order)
|
||||||
{
|
{
|
||||||
$gateway = Omnipay::create('Alipay_AopF2F');
|
try {
|
||||||
$gateway->setSignType('RSA2'); //RSA/RSA2
|
$gateway = new \Library\AlipayF2F();
|
||||||
$gateway->setAppId($this->config['app_id']);
|
$gateway->setAppId($this->config['app_id']);
|
||||||
$gateway->setPrivateKey($this->config['private_key']); // 可以是路径,也可以是密钥内容
|
$gateway->setPrivateKey($this->config['private_key']); // 可以是路径,也可以是密钥内容
|
||||||
$gateway->setAlipayPublicKey($this->config['public_key']); // 可以是路径,也可以是密钥内容
|
$gateway->setAlipayPublicKey($this->config['public_key']); // 可以是路径,也可以是密钥内容
|
||||||
$gateway->setNotifyUrl($order['notify_url']);
|
$gateway->setNotifyUrl($order['notify_url']);
|
||||||
$request = $gateway->purchase();
|
$gateway->setBizContent([
|
||||||
$request->setBizContent([
|
|
||||||
'subject' => config('v2board.app_name', 'V2Board') . ' - 订阅',
|
'subject' => config('v2board.app_name', 'V2Board') . ' - 订阅',
|
||||||
'out_trade_no' => $order['trade_no'],
|
'out_trade_no' => $order['trade_no'],
|
||||||
'total_amount' => $order['total_amount'] / 100
|
'total_amount' => $order['total_amount'] / 100
|
||||||
]);
|
]);
|
||||||
/** @var \Omnipay\Alipay\Responses\AopTradePreCreateResponse $response */
|
$gateway->send();
|
||||||
$response = $request->send();
|
|
||||||
$result = $response->getAlipayResponse();
|
|
||||||
if ($result['code'] !== '10000') {
|
|
||||||
abort(500, $result['sub_msg']);
|
|
||||||
}
|
|
||||||
return [
|
return [
|
||||||
'type' => 0, // 0:qrcode 1:url
|
'type' => 0, // 0:qrcode 1:url
|
||||||
'data' => $response->getQrCode()
|
'data' => $gateway->getQrCodeUrl()
|
||||||
];
|
];
|
||||||
|
} catch (\Exception $e) {
|
||||||
|
abort(500, $e->getMessage());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public function notify($params)
|
public function notify($params)
|
||||||
|
@ -20,7 +20,6 @@
|
|||||||
"laravel/horizon": "^4.3.5",
|
"laravel/horizon": "^4.3.5",
|
||||||
"laravel/tinker": "^2.5",
|
"laravel/tinker": "^2.5",
|
||||||
"linfo/linfo": "^4.0",
|
"linfo/linfo": "^4.0",
|
||||||
"lokielse/omnipay-alipay": "3.1.2",
|
|
||||||
"lokielse/omnipay-wechatpay": "^3.0",
|
"lokielse/omnipay-wechatpay": "^3.0",
|
||||||
"php-curl-class/php-curl-class": "^8.6",
|
"php-curl-class/php-curl-class": "^8.6",
|
||||||
"stripe/stripe-php": "^7.36.1",
|
"stripe/stripe-php": "^7.36.1",
|
||||||
|
164
library/AlipayF2F.php
Normal file
164
library/AlipayF2F.php
Normal file
@ -0,0 +1,164 @@
|
|||||||
|
<?php
|
||||||
|
namespace Library;
|
||||||
|
|
||||||
|
use Illuminate\Support\Facades\Http;
|
||||||
|
|
||||||
|
class AlipayF2F {
|
||||||
|
private $appId;
|
||||||
|
private $privateKey;
|
||||||
|
private $alipayPublicKey;
|
||||||
|
private $signType = 'RSA2';
|
||||||
|
public $bizContent;
|
||||||
|
public $method;
|
||||||
|
public $notifyUrl;
|
||||||
|
public $response;
|
||||||
|
|
||||||
|
public function __construct()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
public function verify($data): bool
|
||||||
|
{
|
||||||
|
if (is_string($data)) {
|
||||||
|
parse_str($data, $data);
|
||||||
|
}
|
||||||
|
$sign = $data['sign'];
|
||||||
|
unset($data['sign']);
|
||||||
|
unset($data['sign_type']);
|
||||||
|
ksort($data);
|
||||||
|
$data = $this->buildQuery($data);
|
||||||
|
$res = "-----BEGIN PUBLIC KEY-----\n" .
|
||||||
|
wordwrap($this->alipayPublicKey, 64, "\n", true) .
|
||||||
|
"\n-----END PUBLIC KEY-----";
|
||||||
|
if ("RSA2" == $this->signType) {
|
||||||
|
$result = (openssl_verify($data, base64_decode($sign), $res, OPENSSL_ALGO_SHA256) === 1);
|
||||||
|
} else {
|
||||||
|
$result = (openssl_verify($data, base64_decode($sign), $res) === 1);
|
||||||
|
}
|
||||||
|
openssl_free_key(openssl_get_publickey($res));
|
||||||
|
return $result;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setBizContent($bizContent = [])
|
||||||
|
{
|
||||||
|
$this->bizContent = json_encode($bizContent);
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setMethod($method)
|
||||||
|
{
|
||||||
|
$this->method = $method;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setAppId($appId)
|
||||||
|
{
|
||||||
|
$this->appId = $appId;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setPrivateKey($privateKey)
|
||||||
|
{
|
||||||
|
$this->privateKey = $privateKey;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setAlipayPublicKey($alipayPublicKey)
|
||||||
|
{
|
||||||
|
$this->alipayPublicKey = $alipayPublicKey;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function setNotifyUrl($url)
|
||||||
|
{
|
||||||
|
$this->notifyUrl = $url;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function send()
|
||||||
|
{
|
||||||
|
$response = Http::get('https://openapi.alipay.com', $this->buildParam())->json();
|
||||||
|
$resKey = str_replace('.', '_', $this->method) . '_response';
|
||||||
|
if (!isset($response[$resKey])) throw new \Exception('从支付宝请求失败');
|
||||||
|
$response = $response[$resKey];
|
||||||
|
if ($response['msg'] !== 'Success') throw new \Exception($response['sub_msg']);
|
||||||
|
$this->response = $response;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function getQrCodeUrl()
|
||||||
|
{
|
||||||
|
$response = $this->response;
|
||||||
|
if (!isset($response['qr_code'])) throw new \Exception('获取付款二维码失败');
|
||||||
|
return $response['qr_code'];
|
||||||
|
}
|
||||||
|
|
||||||
|
public function getResponse()
|
||||||
|
{
|
||||||
|
return $this->response;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function buildParam(): array
|
||||||
|
{
|
||||||
|
$params = [
|
||||||
|
'app_id' => $this->appId,
|
||||||
|
'method' => $this->method,
|
||||||
|
'charset' => 'UTF-8',
|
||||||
|
'sign_type' => $this->signType,
|
||||||
|
'timestamp' => date('Y-m-d H:m:s'),
|
||||||
|
'biz_content' => $this->bizContent,
|
||||||
|
'version' => '1.0',
|
||||||
|
'_input_charset' => 'UTF-8'
|
||||||
|
];
|
||||||
|
if ($this->notifyUrl) $params['notify_url'] = $this->notifyUrl;
|
||||||
|
ksort($params);
|
||||||
|
$params['sign'] = $this->buildSign($this->buildQuery($params));
|
||||||
|
return $params;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function buildQuery($query)
|
||||||
|
{
|
||||||
|
if (!$query) {
|
||||||
|
throw new \Exception('参数构造错误');
|
||||||
|
}
|
||||||
|
//将要 参数 排序
|
||||||
|
ksort($query);
|
||||||
|
|
||||||
|
//重新组装参数
|
||||||
|
$params = array();
|
||||||
|
foreach ($query as $key => $value) {
|
||||||
|
$params[] = $key . '=' . $value;
|
||||||
|
}
|
||||||
|
$data = implode('&', $params);
|
||||||
|
return $data;
|
||||||
|
}
|
||||||
|
|
||||||
|
private function buildSign(string $signData): string
|
||||||
|
{
|
||||||
|
$privateKey = $this->privateKey;
|
||||||
|
$p_key = array();
|
||||||
|
//如果私钥是 1行
|
||||||
|
if (!stripos($privateKey, "\n")) {
|
||||||
|
$i = 0;
|
||||||
|
while ($key_str = substr($privateKey, $i * 64, 64)) {
|
||||||
|
$p_key[] = $key_str;
|
||||||
|
$i++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
$privateKey = "-----BEGIN RSA PRIVATE KEY-----\n" . implode("\n", $p_key);
|
||||||
|
$privateKey = $privateKey . "\n-----END RSA PRIVATE KEY-----";
|
||||||
|
|
||||||
|
//私钥
|
||||||
|
$privateId = openssl_pkey_get_private($privateKey, '');
|
||||||
|
|
||||||
|
// 签名
|
||||||
|
$signature = '';
|
||||||
|
|
||||||
|
if ("RSA2" == $this->signType) {
|
||||||
|
|
||||||
|
openssl_sign($signData, $signature, $privateId, OPENSSL_ALGO_SHA256);
|
||||||
|
} else {
|
||||||
|
|
||||||
|
openssl_sign($signData, $signature, $privateId, OPENSSL_ALGO_SHA1);
|
||||||
|
}
|
||||||
|
|
||||||
|
openssl_free_key($privateId);
|
||||||
|
|
||||||
|
//加密后的内容通常含有特殊字符,需要编码转换下
|
||||||
|
$signature = base64_encode($signature);
|
||||||
|
return $signature;
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user