抖音小程序集成支付宝支付,含代码 |
您所在的位置:网站首页 › 字节跳动小程序平台要收费吗 › 抖音小程序集成支付宝支付,含代码 |
文档地址
收银台(字节跳动小程序)接入文档: https://microapp.bytedance.com/docs/payment/#给开发者使用的服务端下单接口 字节跳动小程序官方开发文档 : https://www.w3cschool.cn/microapp/microapp-aup333iu.html 抖音小程序入口介绍: https://forum.microapp.bytedance.com/mini-app 申请开通支付申请开通支付功能时,需要在小程序开发者的后台提交申请, 如下图所示,并且提供以下资料: 商户名称(公司名称) 法人姓名 渠道支付的业务场景(暂时只支持支付宝App支付,未来会支持微信支付等更多支付方式) 支付类型(开发者勾选):虚拟支付 实物支付 渠道密钥类型(开发者勾选):RSA2 RSA 支付场景描述(描述会使用支付的场景,注意iOS上虚拟物品不支持使用支付宝/微信支付,有虚拟物品支付的开发者,只能在安卓端上使用支付功能)
package com.austin.microapp.common.alipay; import com.alipay.api.AlipayApiException; import com.alipay.api.AlipayClient; import com.alipay.api.DefaultAlipayClient; import com.alipay.api.domain.AlipayTradeAppPayModel; import com.alipay.api.internal.util.AlipaySignature; import com.alipay.api.request.AlipayTradeAppPayRequest; import com.alipay.api.response.AlipayTradeAppPayResponse; import com.austin.microapp.common.utils.CommonUtil; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import javax.servlet.http.HttpServletRequest; import java.util.HashMap; import java.util.Iterator; import java.util.Map; /** * @description */ public class Alipaytrade { private static Logger logger = LoggerFactory.getLogger(Alipaytrade.class); //签名方式 private static final String SIGN_TYPE = "RSA2"; //编码格式 private static final String CHARSET = "utf-8"; public static String appPay(String totalAmount) { String APP_ID="支付宝应用的appid"; String APP_PRIVATE_KEY="支付宝应用私钥,就是用支付宝工具生成的私钥"; String ALIPAY_PUBLIC_KEY="支付宝公钥,就是在支付宝后台上传完公钥后生成的支付宝公钥"; //签名方式 String sign_type="RSA2"; //编码格式 String CHARSET="utf-8"; //正式环境支付宝网关,如果是沙箱环境需更改成https://openapi.alipaydev.com/gateway.do String url="https://openapi.alipay.com/gateway.do"; //实例化客户端 AlipayClient alipayClient = new DefaultAlipayClient(url, APP_ID, APP_PRIVATE_KEY, "json", CHARSET, ALIPAY_PUBLIC_KEY,sign_type); //实例化具体API对应的request类,类名称和接口名称对应,当前调用接口名称:alipay.trade.app.pay AlipayTradeAppPayRequest request = new AlipayTradeAppPayRequest(); //SDK已经封装掉了公共参数,这里只需要传入业务参数。以下方法为sdk的model入参方式(model和biz_content同时存在的情况下取biz_content)。 AlipayTradeAppPayModel model = new AlipayTradeAppPayModel(); model.setBody("我是测试数据"); //请保证OutTradeNo值每次保证唯一 model.setOutTradeNo(CommonUtil.getOrderNo()); model.setSubject("字节跳动-订单编号"+model.getOutTradeNo()); model.setTimeoutExpress("30m"); model.setTotalAmount("0.01"); model.setProductCode("QUICK_MSECURITY_PAY"); request.setBizModel(model); request.setNotifyUrl("商户外网可以访问的异步地址"); try { //这里和普通的接口调用不同,使用的是sdkExecute AlipayTradeAppPayResponse response = alipayClient.sdkExecute(request); //就是orderString 可以直接给客户端请求,无需再做处理。 String result = response.getBody(); //就是orderString 可以直接给客户端请求,无需再做处理。 System.out.println(result); return result; } catch (AlipayApiException e) { e.printStackTrace(); } return ""; } /** * 支付宝支付回调 * @param alipayPublicKey * @param request * @return */ public static String AlipayCallBack(String alipayPublicKey,HttpServletRequest request) { Map result = new HashMap(); Map requestParams = request.getParameterMap(); for (Iterator iter = requestParams.keySet().iterator(); iter.hasNext(); ) { String name = (String) iter.next(); String[] values = (String[]) requestParams.get(name); String valueStr = ""; for (int i = 0; i < values.length; i++) { valueStr = (i == values.length - 1) ? valueStr + values[i] : valueStr + values[i] + ","; } //乱码解决,这段代码在出现乱码时使用。 //valueStr = new String(valueStr.getBytes("ISO-8859-1"), "utf-8"); result.put(name, valueStr); } String outTradeNo = result.get("out_trade_no"); String appId = result.get("app_id"); String sellerId = result.get("out_trade_no"); String totalAmount = result.get("total_amount"); logger.info("outTradeNo=={},appId=={},sellerId=={},totalAmount=={}",outTradeNo,appId,sellerId,totalAmount); //切记alipaypublickey是支付宝的公钥,请去open.alipay.com对应应用下查看。 //boolean AlipaySignature.rsaCheckV1(Map params, String publicKey, String charset, String sign_type) try { boolean flag = AlipaySignature.rsaCheckV1(result, alipayPublicKey, CHARSET, SIGN_TYPE); if (flag) { return "success"; } else { return "failure"; } } catch (AlipayApiException e) { e.printStackTrace(); return "failure"; } } public static void main(String[] args) { // appPay("0.01"); } } 2、字节跳动接入支付宝支付 注意: total_amount参数是Long,分为单位, 发送请求时Content-Type为application/x-www-form-urlencoded HttpsURLConnection conn = (HttpsURLConnection) url.openConnection(); conn.setSSLSocketFactory(ssf); conn.setDoOutput(true); conn.setDoInput(true); conn.setUseCaches(false); // 设置请求方式(GET/POST) conn.setRequestMethod(requestMethod); conn.setRequestProperty("content-type", "application/x-www-form-urlencoded"); package com.austin.microapp.common.toutiao; import com.austin.microapp.common.alipay.Alipaytrade; import com.austin.microapp.common.utils.AESDecodeUtils; import com.austin.microapp.common.utils.CommonUtil; import com.austin.microapp.common.utils.PayCommonUtil; import net.sf.json.JSONObject; import org.apache.tomcat.util.codec.binary.Base64; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import java.util.*; /** * @description */ public class TouTiaoMicroApp { private static Logger logger = LoggerFactory.getLogger(TouTiaoMicroApp.class); /** * 通过login接口获取到登录凭证后,开发者可以通过服务器发送请求的方式获取session_key和openId * https://developer.toutiao.com/docs/server/auth/jscode2session.html * @param appid * @param appSecrect * @param code * @return */ public static JSONObject jscode2session(String appid, String appSecrect, String code) { String strUrl = TouTiaoMicroAppUrls.JSCODE2_SESSION + "?appid=" + appid + "&secret=" + appSecrect + "&code=" + code; JSONObject result = JSONObject.fromObject(CommonUtil.httpsRequest(strUrl, "GET", null)); logger.info("jscode2session result==={}", result); return result; } /** * 获取手机号 * https://developer.toutiao.com/docs/comp/getPhoneNumber.html * @param appid * @param appSecrect * @param code * @param encryptedData * @param iv * @return */ public static JSONObject getPhoneNumber(String appid, String appSecrect, String code, String encryptedData, String iv) { JSONObject jsonObject = jscode2session(appid, appSecrect, code); byte[] encrypData = Base64.decodeBase64(encryptedData); byte[] ivData = Base64.decodeBase64(iv); byte[] sessionKey = Base64.decodeBase64(jsonObject.getString("session_key")); try { String str = AESDecodeUtils.decrypt(sessionKey, ivData, encrypData); JSONObject result = JSONObject.fromObject(str); logger.info("getPhoneNumber result==={}", result); return result; } catch (Exception e) { e.printStackTrace(); logger.error("error==={}", e.getMessage()); return null; } } /** * https://developer.toutiao.com/docs/payment/#给开发者使用的服务端下单接口 * https://developer.toutiao.com/docs/open/requestPayment.html#输入 * @param * @return */ public static JSONObject payment() { Map parameters = new HashMap(); //支付分配给业务方的ID,用于获取签名/验签的密钥信息,不是小程序appid parameters.put("app_id", "支付分配给业务方的appid"); //接口名称 parameters.put("method", "tp.trade.create"); //仅支持JSON parameters.put("format", "JSON"); //请求使用的编码格式,如utf-8、gbk、gb2312等,目前只支持utf-8 parameters.put("charset", "utf-8"); //商户生成签名字符串所使用的签名算法类型,目前支持MD5 RSA2 parameters.put("sign_type", "MD5"); //发送请求的时间,发送请求的时间,长整型的时间戳,单位是秒 parameters.put("timestamp", Long.toString(System.currentTimeMillis() / 1000)); //调用的接口版本,固定为:1.0 parameters.put("version", "1.0"); //请求参数的集合,最大长度不限,除公共参数外所有请求参数都必须放在这个参数中传递,json格式 Map bizContent = new HashMap(); //订单号 bizContent.put("out_order_no", Long.toString(System.currentTimeMillis())); //唯一标识用户的id,小程序开发者请传open_id。open_id获取方法 bizContent.put("uid", "小程序用户open_id"); //小程序开发者可不传,请忽略 // bizContent.put("uid_type",""); //支付分配给业务方的商户号 bizContent.put("merchant_id", "支付分配给业务方的商户号"); //金额,分为单位,应传整型 bizContent.put("total_amount", 1); //币种 bizContent.put("currency", "CNY"); //商户订单名称 bizContent.put("subject", "商户订单名称"); //商户订单详情 bizContent.put("body", "支付宝支付"); //折扣 格式(3段):订单号^金额^方式|订单号^金额^方式。方式目前仅支持红包: coupon如:423423^1^coupon。可选,目前暂不支持 // bizContent.put("pay_discount","combine"); //下单时间戳,unix时间戳 bizContent.put("trade_time", Long.toString(System.currentTimeMillis() / 1000)); //订单有效时间(单位 秒) bizContent.put("valid_time", "180"); //服务器异步通知http地址,请填支付宝下单接口对应的异步通知url bizContent.put("notify_url", "服务器异步通知http地址,请填支付宝下单接口对应的异步通知url"); //平台手续费 // bizContent.put("service_fee",""); //风控信息,标准的json字符串格式,目前需要传入用户的真实ip:"{"ip":"123.123.123.1"}" "{\"ip\":" + 获取Ip地址+ "}" Map riskInfo = new HashMap(); riskInfo.put("ip","123.123.123.1"); com.alibaba.fastjson.JSONObject ipJson = new com.alibaba.fastjson.JSONObject(riskInfo); bizContent.put("risk_info", ipJson); //biz_content是请求参数的集合,最大长度不限,除公共参数外所有请求参数都必须放在这个参数中传递,json格式 com.alibaba.fastjson.JSONObject bizContentJson = new com.alibaba.fastjson.JSONObject(bizContent); parameters.put("biz_content", bizContentJson.toString()); String sign = PayCommonUtil.toutiaoAlipaySign(parameters, "支付分配给业务方秘钥secret"); //商户请求参数的签名串,详见签名方法 // parameters.put("sign", sign); String requestParam = PayCommonUtil.toutiaoAlipaySign(parameters,null)+"&sign="+sign; String result = CommonUtil.httpsRequest(TouTiaoMicroAppUrls.PAYMENT, "POST", requestParam); Map payParams = new HashMap(); payParams.put("app_id","支付分配给业务方的appid"); payParams.put("sign_type","MD5"); payParams.put("timestamp",Long.toString(System.currentTimeMillis()/1000)); JSONObject jsonObject = JSONObject.fromObject(result); String sign2 = jsonObject.getString("sign"); logger.info("payment sign2==={}",sign2); JSONObject data = JSONObject.fromObject(jsonObject.getString("response")); String code = data.getString("code"); String msg = data.getString("msg"); String tradeNo = data.getString("trade_no"); logger.info("payment code==={},msg==={},trade_no==={}",code,msg,tradeNo); payParams.put("trade_no",tradeNo); payParams.put("merchant_id","支付分配给业务方的商户号"); payParams.put("uid","小程序用户open_id"); payParams.put("total_amount",1); //获取调起支付宝支付的url,如:alipay_sdk=alipay-sdk-java-3.7.4.ALL&app_id=2018041302549907&biz_content=%7B%22body%22%3A%22novel%22%2C%22subject%22%3A%22%E6%B5%8B%E8%AF%95%E7%9A%84%E5%95%86%E5%93%81%22%2C%22out_trade_no%22%3A%22201808211756233909095950%22%2C%22timeout_express%22%3A%2230m%22%2C%22total_amount%22%3A%220.01%22%2C%22seller_id%22%3A%22jrtoutiaoyxgs%40bytedance.com%22%2C%22product_code%22%3A%22QUICK_MSECURITY_PAY%22%7D&8&format=JSON&method=alipay.trade.app.pay¬ify_url=https%3A%2F%2Ftp-pay-test.snssdk.com%2Fcallback%2Fali_pay&sign=ZfVkvu%2FSzBqFuqQMgr6MvsXomlr6BCuz7GYDnpsxd3SLVfCssV0q2cnxZyfjh%2FY%2Bk7PO1IeEl4rppQg%2FXgRuIqMXyKdhmigj4oPdQVJEkbSQEcCW4m8mwpXLNjlLH%2FHae3u3hjrMDVPuVXeIxjoq1NLPXy09GY5u1MX8E2lkn8xtmOxA2cXXRIrAa8gTplUoXWkSSkZMgvSTzQ9RjRmlKtK4nERdDWh5RBXLNDU%2FD2FfqIeZuLNZh%2BW8j4dYGtPDm9nWYRz0tLizJDm6E76aTM3qvLi0havCCrHgxZ5d8tVN7GNztA6olbGOiXubEGUq4yBqCojiALEEVpKqfQdZGQ%3D%3D&sign_type=RSA2×tamp=2018-08-21+17%3A56%3A24&version=1.0 String paramsUrl = Alipaytrade.appPay(null); //拼接在字节跳动小程序调起支付宝支付所需参数返回给前端 Map params = new HashMap(); params.put("url",paramsUrl); com.alibaba.fastjson.JSONObject url = new com.alibaba.fastjson.JSONObject(params); payParams.put("params",url); String paySign = PayCommonUtil.toutiaoAlipaySign(payParams,"支付分配给业务方秘钥secret"); payParams.put("method","tp.trade.confirm"); payParams.put("sign",paySign); payParams.put("riskInfoIp","123.123.123.1"); payParams.put("paramsUrl",paramsUrl); payParams.put("pay_channel","ALIPAY_NO_SIGN"); payParams.put("pay_type","ALIPAY_APP"); logger.info("前端调起支付宝支付所需参数payParams==={}",payParams); System.out.println("JSONObject="+JSONObject.fromObject(payParams)); return JSONObject.fromObject(payParams); } public static void main(String[] args) { payment(); } |
今日新闻 |
推荐新闻 |
CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3 |