字节跳动小程序支付

因为业务扩展需求,开发了字节跳动小程序,
记录一下在字节跳动使用支付方法。
因为字节跳动中使用到了,微信及支付宝支付,
建议学习相关支付流程,再进行相关开发。。。
本次使用微信支付获取类为

composer require yansongda/pay -vvv

一、在小程序支付之前我们先要获取相关配置

审核通过以后就能够在小程序开发者后台查看分配的支付 app_id、支付秘钥 secret 和商户号(merchant_id):

$config = array(
    'mch_id'    => '', // 商户号
    'app_id'    => '', // App ID
    'secret'    => '', // 支付secret
    'notify_url' => '', // 支付回调地址
);

二、使用封装好的类,对接支付

<?php
include './BytedancePay.php';
$get = $_GET;

$bytedancepay = new \feng\BytedancePay($config);
$order_sn = time().rand(1000,9999);
$order = array(
    'body'          => '测试商品', // 产品描述
    'total_amount'	=> '1', // 订单金额(分)
    'order_sn'  	=> $order_sn, // 订单编号
);

$re = $bytedancepay->xcxPay($order, $alipayConfig, $wechatConfig);
// 传入支付宝支付及微信支付相关配置,获取支付相关参数
die(json_encode($re)); // JSON化直接返回小程序客户端

三、小程序端相关代码,支付按钮:

<button type="default" size="default" bindtap="pay"> 支付 </button>

index.js pay支付函数

pay: function () {
  // console.log(111)
  tt.request({
    url: "http://ceshi.test/xcxpay.php",
    header: {
      "content-type": "application/json"
    },
    success(res) {
      // console.log(`request调用成功 ${res}`);
      console.log(res);
      if (res.data.code == 1) {
        tt.pay({
            orderInfo: res.data.data,
            _debug: 1
            // ...
        })
      }
    }
  });
},

字节跳动完整支付类 BytedancePay.php 文件:

<?php
/**
 * @Author: [FENG] <1161634940@qq.com>
 * @Date:   2020-05-13 17:02:49
 * @Last Modified by:   [FENG] <1161634940@qq.com>
 * @Last Modified time: 2020-10-30 13:58:54
 */
namespace fengkui;

use Yansongda\Pay\Pay;

/**
 * BytedancePay 字节跳动支付
 */
class BytedancePay
{
    // 支付相关配置
    private static $config = array(
        'mch_id'    => '', // 商户号
        'app_id'    => '', // App ID
        'secret'    => '', // 支付secret
        'notify_url' => '', // 支付回调地址
    );

    /**
     * [__construct 构造函数]
     * @param [type] $config [传递支付相关配置]
     */
    public function __construct($config=NULL){
        $config && self::$config = $config;
    }

    /**
     * [xcxPay 字节跳动小程序支付]
     * @param  string $order [订单信息]
     * @param  string $type  [支付类型 wechat ali]
     * @param  string $url   [对应支付地址]
     * @return [type]        [description]
     * $order = array(
     *      'body'          => '', // 产品描述
     *      'total_amount'  => '', // 订单金额(分)
     *      'order_sn'      => '', // 订单编号
     * );
     */
    public static function xcxPay($order='', $alipay=[], $wechat=[])
    {
        if (!is_array($order) || count($order) < 3 || (!$alipay && !$wechat))
            die("数组数据信息缺失!");

        $config = self::$config;
        $time = time();
        $data = [
            "app_id"        => $config['app_id'],
            "sign_type"     => "MD5",
            "out_order_no"  => (string)$order['order_sn'],
            "merchant_id"   => $config['mch_id'],
            "timestamp"     => (string)$time,
            "product_code"  => "pay",
            "payment_type"  => "direct",
            "total_amount"  => $order['total_amount'],
            "trade_type"    => "H5",
            "uid"           => self::get_rand_str(),
            "version"       => "2.0",
            "currency"      => "CNY",
            "subject"       => $order['body'],
            "body"          => $order['body'],
            "trade_time"    => (string)$time,
            "valid_time"    => "300",
            "notify_url"    => $config['notify_url'],
            // "risk_info" => json_encode(['ip' => self::get_iP()])
        ];

        if ($alipay) { // 支付宝支付
            $aliOrder = array(
                'out_trade_no'  => $order['order_sn'],
                'total_amount'  => $order['total_amount']/100, // **单位:元**
                'subject'       => $order['body'],
            );
            $alipayUrl = Pay::alipay($alipay)->app($aliOrder);
            $data['alipay_url'] = $alipayUrl->getContent();
        }
        if ($wechat) { // 微信支付
            $wechatOrder = [
                'out_trade_no'  => $order['order_sn'],
                'total_fee'     => $order['total_amount'], // **单位:分**
                'body'          => $order['body'],
            ];
            $wxUrl = Pay::wechat($wechat)->wap($wechatOrder);
            $data['wx_url'] = $wxUrl->getTargetUrl();
            $data['wx_type'] = 'MWEB';
        }
        $data["sign"] = self::makeSign($data, $config['secret']);
        $data["risk_info"] = json_encode(['ip' => self::get_iP()]);
        return $data;
    }

    /**
     * [makeSign 生成签名]
     * @param  [type] $data   [入参数据]
     * @param  string $secret [微信支付秘钥]
     * @return [type]         [description]
     */
    protected static function makeSign($data, $secret = ''){
        // 获取微信支付秘钥
        // 去空
        $data=array_filter($data);
        //签名步骤一:按字典序排序参数
        ksort($data);
        $string_a=http_build_query($data);
        $string_a=urldecode($string_a);

        //签名步骤二:在string后加入KEY
        //$config=self::$config;
        $string_sign_temp = $string_a . $secret;
        //签名步骤三:MD5加密
        $sign = md5($string_sign_temp);
        // 签名步骤四:所有字符转为大写
        // $result=strtoupper($sign);
        return $sign;
    }

    /**
     * [get_rand_str 产生随机字符串,不长于32位]
     * @param  integer $length [长度]
     * @return [type]          [description]
     */
    protected static function get_rand_str($length = 32) {
        $chars = "abcdefghijklmnopqrstuvwxyz0123456789";
        $str ="";
        for ( $i = 0; $i < $length; $i++ )  {
            $str .= substr($chars, mt_rand(0, strlen($chars)-1), 1);
        }
        return $str;
    }

    /** fengkui.net
     * [get_iP 定义一个函数get_iP() 客户端IP]
     * @return [type] [description]
     */
    public static function get_iP()
    {
        if (getenv("HTTP_CLIENT_IP"))
            $ip = getenv("HTTP_CLIENT_IP");
        else if(getenv("HTTP_X_FORWARDED_FOR"))
            $ip = getenv("HTTP_X_FORWARDED_FOR");
        else if(getenv("REMOTE_ADDR"))
            $ip = getenv("REMOTE_ADDR");
        else $ip = "Unknow";

        if(preg_match('/^((?:(?:25[0-5]|2[0-4]\d|((1\d{2})|([1-9]?\d)))\.){3}(?:25[0-5]|2[0-4]\d|((1\d{2})|([1 -9]?\d))))$/', $ip))
            return $ip;
        else
            return '';
    }

}

冯奎博客
请先登录后发表评论
  • latest comments
  • 总共1条评论
冯奎博客

哆啦A梦:博主,可以交换友链吗

2020-11-22 14:52:33 回复

冯奎博客 冯奎博客
  • 岁月清浅 安之若素 回复 哆啦A梦:可以啊,留言链接
  • 2020-11-23 13:06:20 回复
冯奎博客
  • 哆啦A梦 回复 岁月清浅 安之若素:名称:哆啦A梦前端博客链接:https://wdyang.cn我已添加贵站
  • 2020-11-23 21:35:52 回复