因为开发需要,本人也是第一次做支付宝的APP支付,以此记录这次开发过程,以便有同学需要!
准备工作
- 打开支付宝开放平台下载php的sdk官方链接 ,下载完成之后将sdk放在根目录下的extend目录下
- 通过支付宝开放平台配置等得到appid、应用私钥、应用公钥、和支付宝公钥 (这步略过,因为这步是有客户自己配置的)
开发过程
- 在根目录下的config目录下的app.php配置关于支付需要的配置
alipay'=>[
'appId' => '这里填写appid',
'gatewayUrl' => 'https://openapi.alipay.com/gateway.do',
'rsaPublicKey' => '这里填写应用公钥',
'rsaPrivateKey' => ‘这里填写应用私钥',
'alipayrsaPublicKey'=> ‘这里填写支付宝公钥’,
'format' => 'json',
'charset' => 'UTF-8',
'signType' => 'RSA2',
'transport' => 'http',
]
- 在api模块下的controller目录下创建Pay.php
<?php
namespace app\api\controller;
require_once "./extend/alipay/aop/AopClient.php";
require_once "./extend/alipay/aop/request/AlipayTradeAppPayRequest.php";
use think\Request;
use think\Controller;
/**
* 支付宝支付
* Class Pay
* @package app\api\controller
* @author wx:lynntim
*/
class Pay extends Controller
{
/**
* 支付
*/
public function pay(Request $request)
{
if ($request->isPost()) {
// 订单号
$order_number = 'XXXXXX'
// 获取金额
$money = $request->param('money');
// 名称
$body='XXXXXX'
// 异步回调地址,这个后面不能带参数的
$notify_url = 'http://XXXXXX/notify.php';
// 可根据具体需要写出具体需求 可创建支付订单 判断支付成功调用支付方法
// 调用支付宝支付
$str = $this->alipay($body, $money, $order_number , $notify_url );
// 这里要注意json会将支付返回的字符串进行转义,所以必须加上htmlspecialchars_decode避免转义,这个需要注意的!!!
return json(['status' => 200, 'data' => htmlspecialchars_decode($str)]);
}
}
/**
* 支付回调
*/
public function notify(Request $request)
{
// 订单号
$out_trade_no = $request->param('out_trade_no');
// 交易状态
$trade_status = $request->param('trade_status');
// 支付宝交易号
$trade_no = $request->param('trade_no');
if ($trade_status == 'TRADE_FINISHED' || $trade_status == 'TRADE_SUCCESS') {
// 这里进行逻辑判断,如果支付成功,可以改变支付状态,可按照具体情况具体分析
if (true) {
echo 'success';
} else {
echo 'fail';
}
}
} else {
echo "fail";
}
}
/**
* 支付宝支付
* @param $body 名称
* @param $total_amount 价格
* @param $product_code 订单号
* @param $notify_url 回调地址
* @return string
*/
private function alipay($body, $total_amount, $product_code, $notify_url)
{
$aop = new \AopClient();
$aop->gatewayUrl = Config::get('alipay')['gatewayUrl'];
$aop->appId = Config::get('alipay')['appId'];
$aop->rsaPrivateKey = Config::get('alipay')['rsaPrivateKey'];
$aop->format = Config::get('alipay')['format'];
$aop->charset = Config::get('alipay')['charset'];
$aop->signType = Config::get('alipay')['signType'];
$aop->alipayrsaPublicKey = Config::get('alipay')['alipayrsaPublicKey'];
$request = new \AlipayTradeAppPayRequest();
$arr['body'] = $body;
$arr['subject'] = $body;
$arr['out_trade_no'] = $product_code;
$arr['timeout_express'] = '30m';
$arr['total_amount'] = floatval($total_amount);
$arr['product_code'] = 'QUICK_MSECURITY_PAY';
$json = json_encode($arr);
$request->setNotifyUrl($notify_url);
$request->setBizContent($json);
$response = $aop->sdkExecute($request);
return htmlspecialchars($response);
}
}
- 因为支付回调链接是不能带参数的,所以我把notify.php创建在根目录下,采取手动定义路由
<?php
// [ 应用入口文件 ]
namespace think;
// 手动定义路由
$_GET['s'] = '/api/Pay/notify';
// 加载基础文件
require __DIR__ . '/thinkphp/base.php';
// 执行应用并响应
Container::get('app')->run()->send();
注意事项
特别要注意的是返回参数的转义问题,开发过程中使用tp内置的json函数的时候,会将字符串里面的特殊字符进行转义,导致前端调用起支付的时候会报错。这个是特别要注意的。出现转义可以加上htmlspecialchars_decode这个函数,错误如图下: