支付宝支付,,支付就不说了。单说退款,进行退款时有个out_request_no,退款时是可选的。注意(全额退款时是可选的,如果是部分退款,则out_request_no是必选的)
$result = DB::transaction(function () use ($orderObj, $mark, $amount) {
// 取得支付方式相关信息
$parent_order = VirtualCabinetOrder::where('virtual_cabinet_order_id', $orderObj->virtual_cabinet_order_id)->first();
$payment = Payment::find($parent_order->payment_id);
$payment_info = unserialize($payment->payment_info);
$aop = new \AopClient ();
$aop->gatewayUrl = 'https://openapi.alipay.com/gateway.do';
$aop->appId = $payment_info['zfbappid'];
$aop->rsaPrivateKey = $payment_info['rsaPrivateKey'];
$aop->alipayrsaPublicKey = $payment_info['alipayrsaPublicKey'];
$aop->apiVersion = '1.0';
$aop->signType = 'RSA2';
$aop->postCharset = 'UTF-8';
$aop->format = 'json';
$aop->timestamp = date("Y-m-d H:i:s", time());
//已完成的支付宝订单,走这里
if (empty($amount)) {
$amount = $orderObj->pledge_amount;
}
$request = new \AlipayTradeRefundRequest ();
$bizContent = array(
//使用支付宝的外部订单号进行退款
'out_trade_no' => $parent_order->out_trade_no,
'refund_amount' => $amount,
//退款时使用外部订单号,系统中未记录支付宝的订单号
'trade_no' => '',
'refund_reason' => $mark,
'out_request_no' => $parent_order->order_sn . '_' . rand(1000, 9999)
);
$request->setBizContent(json_encode($bizContent));
$result = $aop->execute($request);
$log_result = json_decode(json_encode($result), true);
$log_result['refund_info'] = $parent_order->out_trade_no;
$log_result['bizcontent'] = $bizContent;
$log_result['virtual_cabinet_order_item_id'] = $orderObj->virtual_cabinet_order_item_id;
$responseNode = str_replace(".", "_", $request->getApiMethodName()) . "_response";
$result = self::get_result($result, $responseNode, 'zfb_pay');
return $result;
});
if ($result['status'] == true) {
return [true,'退款成功'];
} else {
return [
false,
'退款失败'
];
}
接下来再说说关于支付宝的预授权套餐,业务场景是一次免押可以租借N件设备,分次归还或者取消,也就意味着需要分成N次进行解冻或者支付,解冻如下
$zfb_info = unserialize($parent_order->zfb_info);
$payment_info = unserialize($payment->payment_info);
$aop = new \AopClient();
$aop->gatewayUrl = $payment_info['gatewayurl'];
$aop->appId = $payment_info['zfbappid'];
$aop->rsaPrivateKey = $payment_info['rsaPrivateKey'];
$aop->alipayrsaPublicKey = $payment_info['alipayrsaPublicKey'];
$aop->apiVersion = '1.0';
$aop->format = "json";
$aop->charset = "utf-8";
$aop->signType = "RSA2";
$aop->timestamp = date("Y-m-d H:i:s", time());
// 判断是否还有待归还的子订单
if (empty($refund_amount)) {
$refund_amount = $order->pledge_amount;
}
$extra_param = "{" . "\"auth_no\":\"" . $zfb_info['zm_order_no'] . "\"," . "\"out_request_no\":\"" . $parent_order->order_sn . '_' . rand(1000,9999) . "\"," . "\"amount\":" . round($refund_amount, 2) . "," . "\"remark\":\"解冻\"" . " }";
$request = new \AlipayFundAuthOrderUnfreezeRequest ();
LogDao::save_log('zfb_preaudit', $extra_param);
$request->setNotifyUrl($payment_info['zfb_rent_notify_url']);
$request->setBizContent($extra_param);
$result = $aop->execute($request);
$responseNode = str_replace(".", "_", $request->getApiMethodName()) . "_response";
$result = self::get_result($result, $responseNode, 'zfb_preaudit');
if ($result['status'] == true) {
if (isset($result['ali_order_no'])) {
$zfb_info[$order->virtual_cabinet_order_item_id . '_ali_orderNo'] = $result['ali_order_no'];
}
$parent_order->zfb_info = serialize($zfb_info);
$parent_order->save();
if ($order->item_order_status == VirtualCabinetConstDao::VIRTUAL_CABINET_ORDER_ITEM_STATUS_WAITING_REFUNDING) {
self::order_status_complete($order, $mark);
} else {
self::order_status_refund($order, $mark);
}
return [
true,
'退款成功'
];
} else {
//退款失败,不作处理,后台进行处理
return [
false,
'退款失败'
];
}
关于预授权转支付,如果需要进行多次转支付,则每次支付的外部订单号需要是不同的
/**
* 支付宝预授权子订单授权转支付
*/
public static function zfb_order_pay_for_preaudit($order, $payment, $amount = 0)
{
if (empty($amount)) {
$amount = $order->pledge_amount;
}
if ($amount < 0.01) {
// 支付金额是0
$result['status'] = true;
return $result;
}
$payment_info = unserialize($payment->payment_info);
$aop = new \AopClient();
$aop->gatewayUrl = $payment_info['gatewayurl'];
$aop->appId = $payment_info['zfbappid'];
$aop->rsaPrivateKey = $payment_info['rsaPrivateKey'];
$aop->alipayrsaPublicKey = $payment_info['alipayrsaPublicKey'];
$aop->apiVersion = '1.0';
$aop->format = "json";
$aop->charset = "utf-8";
$aop->signType = "RSA2";
$aop->timestamp = date("Y-m-d H:i:s", time());
$request = new \AlipayTradePayRequest ();
$parent_order = VirtualCabinetOrder::where('virtual_cabinet_order_id', $order->virtual_cabinet_order_id)->first();
$zfb_info = unserialize($parent_order->zfb_info);
if (empty($amount)) {
$amount = $order->pledge_amount;
}
$bizContent = [
'out_trade_no' => $parent_order->order_sn."_".rand(1000,9999),
"product_code" => 'PRE_AUTH_ONLINE',
'auth_no' => $zfb_info['zm_order_no'],
'subject' => '租金支付',
'total_amount' => $amount,
'remark' => '租金支付',
'seller_id' => $payment_info['zfb_shop_id'],
'buyer_id' => $zfb_info['payer_user_id'],
'store_id' => 21,
'body' => '订单完成支付',
];
LogDao::save_log('zfb_preaudit', array_merge($bizContent, ['virtual_cabinet_order_item_id' => $order->virtual_cabinet_order_item_id]));
$request->setNotifyUrl($payment_info['zfb_rent_notify_url']);
$request->setBizContent(json_encode($bizContent));
$result = $aop->execute($request);
//LogDao::save_log('zfb_preaudit', $result);
$responseNode = str_replace(".", "_", $request->getApiMethodName()) . "_response";
$result = self::get_result($result, $responseNode, 'zfb_preaudit');
return $result;
}