需要用到的链接:
微信支付公钥使用介绍 - 平台证书 | 微信支付商户文档中心
GitHub - wechatpay-apiv3/wechatpay-java: 微信支付 APIv3 的官方 Java Library
谨记 如果有疑问 多看几遍 wechatpay-java的readme 和 example
创建预支付
@Overridepublic ResultBean<OrderPaymentVO> payment(OrderPaymentParam orderPaymentParam, String platform) {log.info("===== 生成预支付订单,参数:{},platform:{}", orderPaymentParam, platform);// 初始化商户配置// 用于公钥//Config config =// new RSAPublicKeyConfig.Builder()// .merchantId(merchantId)// .privateKeyFromPath(privateKeyPath)// .publicKeyFromPath(publicKeyPath)// .publicKeyId(publicKeyId)// .merchantSerialNumber(merchantSerialNumber)// .apiV3Key(apiV3Key)// .build();// 用于秘钥 会自动下载证书 - 暂时不适用// Config config =// new RSAAutoCertificateConfig.Builder()// .merchantId(merchantId)// .privateKeyFromPath(privateKeyPath)// .merchantSerialNumber(merchantSerialNumber)// .apiV3Key(apiV3Key)// .build();Config config =new RSAConfig.Builder().merchantId(merchantId).privateKeyFromPath(privateKeyPath).merchantSerialNumber(merchantSerialNumber).wechatPayCertificatesFromPath(wechatPayCertificatePath).build();// 初始化服务//service = new JsapiService.Builder().config(config).build();JsapiServiceExtension service = new JsapiServiceExtension.Builder().config(config).build();//调用微信支付接口,生成预支付交易单PrepayRequest request = new PrepayRequest();// 设置支付者Payer payer = new Payer();payer.setOpenid(openId);request.setPayer(payer);//设置金额Amount amount = new Amount();amount.setCurrency("CNY");amount.setTotal(payInfo.getAmount().multiply(new BigDecimal(100)).setScale(2, RoundingMode.HALF_UP).intValue());request.setAmount(amount);// appidrequest.setAppid(mircoAppid);request.setDescription(payInfo.getSubject());request.setOutTradeNo(orderPaymentParam.getApplyId());request.setMchid(merchantId);request.setNotifyUrl(notifyUrl);// 发起请求PrepayWithRequestPaymentResponse response = service.prepayWithRequestPayment(request);//构造数据给微信小程序,用于调起微信支付JSONObject jo = new JSONObject();jo.put("timeStamp", response.getTimeStamp());jo.put("nonceStr", response.getNonceStr());jo.put("package", response.getPackageVal());jo.put("signType", response.getSignType());jo.put("paySign", response.getPaySign());OrderPaymentVO vo = jo.toJavaObject(OrderPaymentVO.class);vo.setPackageStr(jo.getString("package"));log.info("===== 生成预支付交易单:{}", vo);return new ResultBean<>(vo);}
支付回调
public void paySuccessNotify(HttpServletRequest request, HttpServletResponse response) throws Exception {String body = readData(request);log.info(request.toString());String wechatpayNonce = request.getHeader("Wechatpay-Nonce");String wechatSignature = request.getHeader("Wechatpay-Signature");String wechatTimestamp = request.getHeader("Wechatpay-Timestamp");String wechatPaySerial = request.getHeader("Wechatpay-Serial");RequestParam requestParam = new RequestParam.Builder().serialNumber(wechatPaySerial).nonce(wechatpayNonce).signature(wechatSignature).timestamp(wechatTimestamp).body(body).build();// 这是秘钥 可下载证书的 这个有点危险,因为下载证书后其他平台可能不一定能用//NotificationConfig config = new RSAAutoCertificateConfig.Builder()// .merchantId(merchantId)// .privateKeyFromPath(privateKeyPath)// .merchantSerialNumber(merchantSerialNumber)// .apiV3Key(apiV3Key)// .build();// 这是在使用原来不变的情况下的代码// 请使用 RSAAutoCertificateConfig,开发者应尽快迁移,我们将在未来某个时间移除这段废弃的代码。NotificationConfig config = new RSANotificationConfig.Builder().apiV3Key(apiV3Key).certificatesFromPath(wechatPayCertificatePath).build();//NotificationConfig config =// new RSAConfig.Builder()// .merchantId(merchantId)// .privateKeyFromPath(privateKeyPath)// .merchantSerialNumber(merchantSerialNumber)// .wechatPayCertificatesFromPath(wechatPayCertificatePath)// .build();// 这是使用公钥的//NotificationConfig config = new RSAPublicKeyConfig.Builder()//.merchantId(merchantId)//.publicKeyFromPath(publicKeyPath)//.publicKeyId(publicKeyId)//.privateKeyFromPath(privateKeyPath)//.merchantSerialNumber(merchantSerialNumber)//.apiV3Key(apiV3Key)//.build();NotificationParser parser = new NotificationParser(config);try {// 以支付通知回调为例,验签、解密并转换成 TransactionTransaction transaction = parser.parse(requestParam, Transaction.class);//String tradeState = jsonObject.getString("trade_state");if (transaction.getTradeState()== Transaction.TradeStateEnum.SUCCESS) {//String outTradeNo = jsonObject.getString("out_trade_no");//商户平台订单号String outTradeNo = transaction.getOutTradeNo();//商户平台订单号String transactionId = transaction.getTransactionId();//微信支付交易号TransactionPayer payer = transaction.getPayer();String openId = payer.getOpenid();//订单金额//JSONObject amount = JSON.parseObject(jsonObject.getString("amount"));//JSONObject amount = JSON.parseObject(transaction.getAmount());TransactionAmount amount = transaction.getAmount();//总金额//String total = amount.getString("total");Integer total =amount.getTotal();//用户支付金额Integer payerTotal = amount.getPayerTotal();/// 自己的逻辑ResponseEntity.status(HttpStatus.OK);} else {log.info("==== update income fail : " + outTradeNo);}}}} catch (ValidationException e) {// 签名验证失败,返回 401 UNAUTHORIZED 状态码log.error("sign verification failed", e);ResponseEntity.status(HttpStatus.UNAUTHORIZED);}}
注意事项:
1. 对于不清楚的,看看官方库的 examplate
2. 本地测试 记得使用端口转发
3. 多看文档