123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675 |
- package com.fuint.common.service.impl;
- import com.alibaba.fastjson.JSON;
- import com.alibaba.fastjson.JSONObject;
- import com.alibaba.fastjson.JSONArray;
- import com.fuint.common.bean.WxPayBean;
- import com.fuint.common.dto.OrderDto;
- import com.fuint.common.dto.UserOrderDto;
- import com.fuint.common.enums.*;
- import com.fuint.common.http.HttpRESTDataClient;
- import com.fuint.common.service.*;
- import com.fuint.common.util.RedisUtil;
- import com.fuint.framework.exception.BusinessCheckException;
- import com.fuint.framework.web.ResponseObject;
- import com.fuint.repository.model.*;
- import com.fuint.utils.StringUtil;
- import com.ijpay.core.enums.SignType;
- import com.ijpay.core.kit.HttpKit;
- import com.ijpay.core.kit.WxPayKit;
- import com.ijpay.wxpay.WxPayApi;
- import com.ijpay.wxpay.WxPayApiConfig;
- import com.ijpay.wxpay.WxPayApiConfigKit;
- import com.ijpay.wxpay.model.MicroPayModel;
- import com.ijpay.wxpay.model.OrderQueryModel;
- import com.ijpay.wxpay.model.RefundModel;
- import com.ijpay.wxpay.model.UnifiedOrderModel;
- import org.bouncycastle.jce.provider.BouncyCastleProvider;
- import org.slf4j.Logger;
- import org.slf4j.LoggerFactory;
- import org.springframework.beans.factory.annotation.Autowired;
- import org.springframework.stereotype.Service;
- import org.springframework.transaction.annotation.Transactional;
- import org.springframework.core.env.Environment;
- import weixin.popular.util.JsonUtil;
- import javax.crypto.Cipher;
- import javax.crypto.spec.IvParameterSpec;
- import javax.crypto.spec.SecretKeySpec;
- import javax.servlet.http.HttpServletRequest;
- import javax.servlet.http.HttpServletResponse;
- import java.io.IOException;
- import java.io.OutputStream;
- import java.math.BigDecimal;
- import java.security.AlgorithmParameters;
- import java.security.Security;
- import java.util.*;
- /**
- * 微信相关接口
- *
- * Created by FSQ
- * CopyRight https://www.fuint.cn
- */
- @Service
- public class WeixinServiceImpl implements WeixinService {
- private static final Logger logger = LoggerFactory.getLogger(WeixinServiceImpl.class);
- @Autowired
- private OrderService orderService;
- @Autowired
- private SettingService settingService;
- @Autowired
- private MessageService messageService;
- @Autowired
- private StoreService storeService;
- @Autowired
- private PaymentService paymentService;
- @Autowired
- private Environment env;
- @Autowired
- WxPayBean wxPayBean;
- private static final String CALL_BACK_URL = "/clientApi/pay/weixinCallback";
- private static final String REFUND_NOTIFY_URL = "/clientApi/pay/weixinRefundNotify";
- /**
- * 获取微信accessToken
- * @param useCache 是否读取缓存
- * @return
- * */
- @Override
- public String getAccessToken(boolean useCache) {
- String wxAppId = env.getProperty("wxpay.appId");
- String wxAppSecret = env.getProperty("wxpay.appSecret");
- String wxTokenUrl = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=%s&secret=%s";
- String url = String.format(wxTokenUrl, wxAppId, wxAppSecret);
- String token = "";
- if (useCache) {
- token = RedisUtil.get("FUINT_ACCESS_TOKEN");
- }
- if (token == null || StringUtil.isEmpty(token)) {
- try {
- String response = HttpRESTDataClient.requestGet(url);
- JSONObject json = (JSONObject) JSONObject.parse(response);
- if (!json.containsKey("errcode")) {
- RedisUtil.set("FUINT_ACCESS_TOKEN", json.get("access_token"), 7200);
- token = (String) json.get("access_token");
- } else {
- logger.error("获取微信accessToken出错:" + json.get("errmsg"));
- }
- } catch (Exception e) {
- logger.error("获取微信accessToken异常:" + e.getMessage());
- }
- }
- return token;
- }
- /**
- * 创建支付订单
- * @return
- * */
- @Override
- @Transactional(rollbackFor = Exception.class)
- public ResponseObject createPrepayOrder(MtUser userInfo, MtOrder orderInfo, Integer payAmount, String authCode, Integer giveAmount, String ip, String platform) throws BusinessCheckException {
- logger.info("WeixinService createPrepayOrder inParams userInfo={} payAmount={} giveAmount={} goodsInfo={}", userInfo, payAmount, giveAmount, orderInfo);
- String goodsInfo = orderInfo.getOrderSn();
- if (orderInfo.getType().equals(OrderTypeEnum.PRESTORE.getKey())) {
- goodsInfo = OrderTypeEnum.PRESTORE.getValue();
- }
- // 1. 调用微信接口生成预支付订单
- Map<String, String> reqData = new HashMap<>();
- reqData.put("body", goodsInfo);
- reqData.put("out_trade_no", orderInfo.getOrderSn());
- reqData.put("device_info", "");
- reqData.put("fee_type", "CNY");
- reqData.put("total_fee", payAmount.toString());
- reqData.put("spbill_create_ip", ip);
- // JSAPI支付
- if (orderInfo.getPayType().equals(PayTypeEnum.JSAPI.getKey())) {
- reqData.put("trade_type", PayTypeEnum.JSAPI.getKey());
- reqData.put("openid", userInfo.getOpenId() == null ? "" : userInfo.getOpenId());
- }
- // 刷卡支付
- if (StringUtil.isNotEmpty(authCode)) {
- reqData.put("auth_code", authCode);
- }
- // 更新支付金额
- BigDecimal payAmount1 = new BigDecimal(payAmount).divide(new BigDecimal("100"));
- OrderDto reqDto = new OrderDto();
- reqDto.setId(orderInfo.getId());
- reqDto.setPayAmount(payAmount1);
- reqDto.setPayType(orderInfo.getPayType());
- orderService.updateOrder(reqDto);
- Map<String, String> respData;
- if (reqData.get("auth_code") != null && StringUtil.isNotEmpty(reqData.get("auth_code"))) {
- respData = microPay(orderInfo.getStoreId(), reqData, ip, platform);
- } else {
- respData = jsapiPay(orderInfo.getStoreId(), reqData, ip, platform);
- }
- if (respData == null) {
- logger.error("微信支付接口调用异常......");
- return new ResponseObject(3000, "微信支付接口调用异常", null);
- }
- // 2.更新预支付订单号
- if (respData.get("return_code").equals("SUCCESS")) {
- if (respData.get("trade_type").equals(PayTypeEnum.JSAPI.getKey())) {
- String prepayId = respData.get("prepay_id");
- getApiConfig(orderInfo.getStoreId(), platform);
- WxPayApiConfig wxPayApiConfig = WxPayApiConfigKit.getWxPayApiConfig();
- respData = WxPayKit.miniAppPrepayIdCreateSign(wxPayApiConfig.getAppId(), prepayId, wxPayApiConfig.getPartnerKey(), SignType.MD5);
- String jsonStr = JSON.toJSONString(respData);
- logger.info("小程序支付的参数:" + jsonStr);
- }
- } else {
- logger.error("微信支付接口返回状态失败......" + respData.toString() + "...reason");
- return new ResponseObject(3000, "微信支付接口返回状态失败", null);
- }
- ResponseObject responseObject = new ResponseObject(200, "微信支付接口返回成功", respData);
- logger.info("WXService createPrepayOrder outParams {}", responseObject.toString());
- return responseObject;
- }
- public Map<String, String> processResXml(HttpServletRequest request) {
- try {
- String xmlMsg = HttpKit.readData(request);
- logger.info("支付通知=" + xmlMsg);
- Map<String, String> result = WxPayKit.xmlToMap(xmlMsg);
- String returnCode = result.get("return_code");
- getApiConfig(0, PlatformTypeEnum.MP_WEIXIN.getCode());
- if (WxPayKit.verifyNotify(result, WxPayApiConfigKit.getWxPayApiConfig().getPartnerKey(), SignType.MD5)) {
- if (WxPayKit.codeIsOk(returnCode)) {
- return result;
- }
- }
- } catch (Exception e) {
- logger.error(e.getMessage(), e);
- }
- return null;
- }
- public void processRespXml(HttpServletResponse response, boolean flag){
- Map<String,String> respData = new HashMap<>();
- if (flag) {
- respData.put("return_code", "SUCCESS");
- respData.put("return_msg", "OK");
- }else{
- respData.put("return_code", "FAIL");
- respData.put("return_msg", "FAIL");
- }
- OutputStream outputStream = null;
- try {
- String respXml = WxPayKit.toXml(respData);
- outputStream = response.getOutputStream();
- outputStream.write(respXml.getBytes("UTF-8"));
- outputStream.flush();
- } catch (Exception e) {
- e.printStackTrace();
- }finally {
- if(outputStream!=null){
- try {
- outputStream.close();
- } catch (IOException e) {
- logger.error(e.getMessage(), e);
- }
- }
- }
- }
- /**
- * 获取微信个人信息
- * @return
- * */
- @Override
- public JSONObject getWxProfile(String code) {
- String wxAppId = env.getProperty("wxpay.appId");
- String wxAppSecret = env.getProperty("wxpay.appSecret");
- String wxAccessUrl = "https://api.weixin.qq.com/sns/jscode2session?appid=%s&secret=%s&js_code=%s&grant_type=authorization_code";
- String url = String.format(wxAccessUrl, wxAppId, wxAppSecret, code);
- try {
- String response = HttpRESTDataClient.requestGet(url);
- JSONObject json = (JSONObject) JSONObject.parse(response);
- if (!json.containsKey("errcode")) {
- return json;
- } else {
- logger.error("获取微信getWxProfile出错:code = " + json.containsKey("errcode") + ",msg="+ json.get("errmsg"));
- }
- } catch (Exception e) {
- logger.error("获取微信getWxProfile异常:" + e.getMessage());
- }
- return null;
- }
- /**
- * 获取公众号openId
- * @return
- * */
- @Override
- public JSONObject getWxOpenId(String code) {
- String wxAppId = env.getProperty("weixin.official.appId");
- String wxAppSecret = env.getProperty("weixin.official.appSecret");
- String wxAccessUrl = "https://api.weixin.qq.com/sns/oauth2/access_token?appid=%s&secret=%s&code=%s&grant_type=authorization_code";
- String url = String.format(wxAccessUrl, wxAppId, wxAppSecret, code);
- try {
- String response = HttpRESTDataClient.requestGet(url);
- JSONObject json = (JSONObject) JSONObject.parse(response);
- if (!json.containsKey("errcode")) {
- return json;
- } else {
- logger.error("获取openId出错:code = " + json.containsKey("errcode") + ",msg="+ json.get("errmsg"));
- }
- } catch (Exception e) {
- logger.error("获取微信openId异常:" + e.getMessage());
- }
- return null;
- }
- /**
- * 获取微信绑定手机号
- * @return
- * */
- @Override
- public String getPhoneNumber(String encryptedData, String sessionKey, String iv) {
- // 被加密的数据
- byte[] dataByte = Base64.getDecoder().decode(encryptedData);
- // 加密秘钥
- byte[] keyByte = Base64.getDecoder().decode(sessionKey);
- // 偏移量
- byte[] ivByte = Base64.getDecoder().decode(iv);
- try {
- // 如果密钥不足16位,那么就补足. 这个if 中的内容很重要
- int base = 16;
- if (keyByte.length % base != 0) {
- int groups = keyByte.length / base + (keyByte.length % base != 0 ? 1 : 0);
- byte[] temp = new byte[groups * base];
- Arrays.fill(temp, (byte) 0);
- System.arraycopy(keyByte, 0, temp, 0, keyByte.length);
- keyByte = temp;
- }
- // 初始化
- Security.addProvider(new BouncyCastleProvider());
- Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
- SecretKeySpec spec = new SecretKeySpec(keyByte, "AES");
- AlgorithmParameters parameters = AlgorithmParameters.getInstance("AES");
- parameters.init(new IvParameterSpec(ivByte));
- cipher.init(Cipher.DECRYPT_MODE, spec, parameters);// 初始化
- byte[] resultByte = cipher.doFinal(dataByte);
- if (null != resultByte && resultByte.length > 0) {
- String result = new String(resultByte, "UTF-8");
- JSONObject object = JSONObject.parseObject(result);
- return object.getString("phoneNumber");
- }
- } catch (Exception e) {
- e.printStackTrace();
- }
- return null;
- }
- /**
- * 发送订阅消息
- * @return
- * */
- @Override
- public Boolean sendSubscribeMessage(Integer merchantId, Integer userId, String toUserOpenId, String key, String page, Map<String,Object> params, Date sendTime) throws BusinessCheckException {
- if (StringUtil.isEmpty(toUserOpenId) || StringUtil.isEmpty(key) || userId < 1) {
- return false;
- }
- MtSetting mtSetting = settingService.querySettingByName(merchantId, key);
- if (mtSetting == null) {
- return false;
- }
- JSONObject jsonObject = null;
- String templateId = "";
- JSONArray paramArray = null;
- try {
- if (mtSetting != null && mtSetting.getValue().indexOf('}') > 0) {
- jsonObject = JSONObject.parseObject(mtSetting.getValue());
- }
- if (jsonObject != null) {
- templateId = jsonObject.get("templateId").toString();
- paramArray = (JSONArray) JSONObject.parse(jsonObject.get("params").toString());
- }
- } catch (Exception e) {
- logger.info("WeixinService sendSubscribeMessage parse setting error={}", mtSetting);
- }
- if (StringUtil.isEmpty(templateId) || paramArray.size() < 1) {
- logger.info("WeixinService sendSubscribeMessage setting error={}", mtSetting);
- return false;
- }
- JSONObject jsonData = new JSONObject();
- jsonData.put("touser", toUserOpenId); // 接收者的openid
- jsonData.put("template_id", templateId);
- if (StringUtil.isEmpty(page)) {
- page = "pages/index/index";
- }
- jsonData.put("page", page);
- // 组装参数
- JSONObject data = new JSONObject();
- for (int i = 0; i < paramArray.size(); i++) {
- JSONObject para = paramArray.getJSONObject(i);
- String value = para.get("value").toString().replaceAll("\\{", "").replaceAll(".DATA}}", "");
- String paraKey = para.get("key").toString();
- String paraValue = params.get(paraKey).toString();
- JSONObject arg = new JSONObject();
- arg.put("value", paraValue);
- data.put(value, arg);
- }
- jsonData.put("data", data);
- String reqDataJsonStr = JSON.toJSONString(jsonData);
- // 存储到消息表里,后续通过定时任务发送
- MtMessage mtMessage = new MtMessage();
- mtMessage.setUserId(userId);
- mtMessage.setType(MessageEnum.SUB_MSG.getKey());
- mtMessage.setTitle(WxMessageEnum.getValue(key));
- mtMessage.setContent(WxMessageEnum.getValue(key));
- mtMessage.setIsRead(YesOrNoEnum.NO.getKey());
- mtMessage.setIsSend(YesOrNoEnum.NO.getKey());
- mtMessage.setSendTime(sendTime);
- mtMessage.setStatus(StatusEnum.ENABLED.getKey());
- mtMessage.setParams(reqDataJsonStr);
- messageService.addMessage(mtMessage);
- return true;
- }
- @Override
- public Boolean doSendSubscribeMessage(String reqDataJsonStr) {
- try {
- String url = "https://api.weixin.qq.com/cgi-bin/message/subscribe/send?access_token=" + this.getAccessToken(true);
- String response = HttpRESTDataClient.requestPost(url, "application/json; charset=utf-8", reqDataJsonStr);
- logger.info("WeixinService sendSubscribeMessage response={}", response);
- JSONObject json = (JSONObject) JSONObject.parse(response);
- if (json.get("errcode").toString().equals("40001")) {
- this.getAccessToken(false);
- logger.error("发送订阅消息出错error1:" + json.get("errcode").toString());
- return false;
- } else if (!json.get("errcode").toString().equals("0")) {
- logger.error("发送订阅消息出错error2:" + json.get("errcode").toString());
- return false;
- } else {
- return true;
- }
- } catch (Exception e) {
- logger.error("发送订阅消息出错:" + e.getMessage());
- }
- return true;
- }
- /**
- * 查询支付订单
- * */
- @Override
- public Map<String, String> queryPaidOrder(Integer storeId, String transactionId, String orderSn) {
- try {
- getApiConfig(storeId, PlatformTypeEnum.MP_WEIXIN.getCode());
- WxPayApiConfig wxPayApiConfig = WxPayApiConfigKit.getWxPayApiConfig();
- Map<String, String> params = OrderQueryModel.builder()
- .appid(wxPayApiConfig.getAppId())
- .mch_id(wxPayApiConfig.getMchId())
- .transaction_id(transactionId)
- .out_trade_no(orderSn)
- .nonce_str(WxPayKit.generateStr())
- .build()
- .createSign(wxPayApiConfig.getPartnerKey(), SignType.MD5);
- logger.info("请求参数:{}", WxPayKit.toXml(params));
- String query = WxPayApi.orderQuery(params);
- Map<String, String> result = WxPayKit.xmlToMap(query);
- logger.info("查询结果: {}", result);
- if (result.get("result_code").equals("FAIL")) {
- result.put("trade_state", "FAIL");
- }
- return result;
- } catch (Exception e) {
- e.printStackTrace();
- return null;
- }
- }
- /**
- * 刷卡支付
- * */
- private Map<String, String> microPay(Integer storeId, Map<String, String> reqData, String ip, String platform) {
- try {
- String orderSn = reqData.get("out_trade_no");
- logger.info("调用微信刷卡支付下单接口入参{}", JsonUtil.toJSONString(reqData));
- logger.info("请求平台:{}, 订单号:{}", platform, orderSn);
- // 支付配置
- getApiConfig(storeId, platform);
- WxPayApiConfig wxPayApiConfig = WxPayApiConfigKit.getWxPayApiConfig();
- Map<String, String> params = MicroPayModel.builder()
- .appid(wxPayApiConfig.getAppId())
- .mch_id(wxPayApiConfig.getMchId())
- .nonce_str(WxPayKit.generateStr())
- .body(reqData.get("body"))
- .attach(reqData.get("body"))
- .out_trade_no(orderSn)
- .total_fee(reqData.get("total_fee"))
- .spbill_create_ip(ip)
- .auth_code(reqData.get("auth_code"))
- .build()
- .createSign(wxPayApiConfig.getPartnerKey(), SignType.MD5);
- String xmlResult = WxPayApi.microPay(false, params);
- // 同步返回结果
- logger.info("xmlResult:" + xmlResult);
- Map<String, String> respMap = WxPayKit.xmlToMap(xmlResult);
- String returnCode = respMap.get("return_code");
- String returnMsg = respMap.get("return_msg");
- if (!WxPayKit.codeIsOk(returnCode)) {
- // 通讯失败
- Map<String, String> payResult = null;
- String errCode = respMap.get("err_code");
- if (StringUtil.isNotEmpty(errCode)) {
- // 用户支付中,需要输入密码
- if (errCode.equals("USERPAYING")) {
- // 等待10秒后查询订单
- try {
- Thread.sleep(10000);
- } catch (InterruptedException e) {
- e.printStackTrace();
- }
- payResult = queryPaidOrder(storeId, respMap.get("transaction_id"), orderSn);
- }
- }
- if (payResult == null || !payResult.get("trade_state").equals("SUCCESS")) {
- logger.info("提交刷卡支付失败>>" + xmlResult);
- return respMap;
- }
- }
- String resultCode = respMap.get("result_code");
- if (!WxPayKit.codeIsOk(resultCode)) {
- logger.info("支付失败>>" + xmlResult);
- logger.error(returnMsg);
- return respMap;
- }
- // 支付成功
- logger.info("刷卡支付返回>>" + respMap.toString());
- if (StringUtil.isNotEmpty(orderSn)) {
- UserOrderDto orderInfo = orderService.getOrderByOrderSn(orderSn);
- if (orderInfo != null) {
- if (!orderInfo.getStatus().equals(OrderStatusEnum.DELETED.getKey())) {
- paymentService.paymentCallback(orderInfo);
- }
- }
- }
- return respMap;
- } catch (Exception e) {
- logger.error(e.getMessage(), e);
- }
- return null;
- }
- /**
- * 小程序、公众号支付
- * */
- private Map<String, String> jsapiPay(Integer storeId, Map<String, String> reqData, String ip, String platform) {
- try {
- logger.info("调用微信支付下单接口入参{}", JsonUtil.toJSONString(reqData));
- logger.info("请求平台:{}", platform);
- // 支付配置
- getApiConfig(storeId, platform);
- WxPayApiConfig wxPayApiConfig = WxPayApiConfigKit.getWxPayApiConfig();
- Map<String, String> params = UnifiedOrderModel
- .builder()
- .appid(wxPayApiConfig.getAppId())
- .mch_id(wxPayApiConfig.getMchId())
- .nonce_str(WxPayKit.generateStr())
- .body(reqData.get("body"))
- .attach(reqData.get("body"))
- .out_trade_no(reqData.get("out_trade_no"))
- .total_fee(reqData.get("total_fee"))
- .spbill_create_ip(ip)
- .notify_url(wxPayApiConfig.getDomain() + CALL_BACK_URL)
- .trade_type(reqData.get("trade_type"))
- .openid(reqData.get("openid"))
- .build()
- .createSign(wxPayApiConfig.getPartnerKey(), SignType.MD5);
- String xmlResult = WxPayApi.pushOrder(false, params);
- logger.info(xmlResult);
- Map<String, String> result = WxPayKit.xmlToMap(xmlResult);
- String returnCode = result.get("return_code");
- String returnMsg = result.get("return_msg");
- if (!WxPayKit.codeIsOk(returnCode)) {
- logger.error(returnMsg);
- }
- String resultCode = result.get("result_code");
- if (!WxPayKit.codeIsOk(resultCode)) {
- logger.error(returnMsg);
- }
- logger.info("调用微信支付下单接口返回{}", JsonUtil.toJSONString(result));
- return result;
- } catch (Exception e) {
- logger.error(e.getMessage(), e);
- }
- return null;
- }
- /**
- * 发起退款
- * @param storeId
- * @param orderSn
- * @param totalAmount
- * @param refundAmount
- * @param platform
- * @return
- * */
- public Boolean doRefund(Integer storeId, String orderSn, BigDecimal totalAmount, BigDecimal refundAmount, String platform) throws BusinessCheckException {
- try {
- logger.info("WeixinService.doRefund orderSn = {}, totalFee = {}, refundFee = {}", orderSn, totalAmount, refundAmount);
- if (StringUtil.isEmpty(orderSn)) {
- throw new BusinessCheckException("退款订单号不能为空...");
- }
- BigDecimal totalFee = totalAmount.multiply(new BigDecimal("100"));
- BigDecimal refundFee = refundAmount.multiply(new BigDecimal("100"));
- Integer totalFeeInt = totalFee.intValue();
- Integer refundFeeInt = refundFee.intValue();
- // 支付配置
- getApiConfig(storeId, platform);
- WxPayApiConfig wxPayApiConfig = WxPayApiConfigKit.getWxPayApiConfig();
- Map<String, String> params = RefundModel.builder()
- .appid(wxPayApiConfig.getAppId())
- .mch_id(wxPayApiConfig.getMchId())
- .nonce_str(WxPayKit.generateStr())
- .transaction_id("")
- .out_trade_no(orderSn)
- .out_refund_no(orderSn)
- .total_fee(totalFeeInt.toString())
- .refund_fee(refundFeeInt.toString())
- .notify_url(wxPayApiConfig.getDomain() + REFUND_NOTIFY_URL)
- .build()
- .createSign(wxPayApiConfig.getPartnerKey(), SignType.MD5);
- String refundStr = WxPayApi.orderRefund(false, params, wxPayApiConfig.getCertPath(), wxPayApiConfig.getMchId());
- logger.info("WeixinService doRefund params: {}", params);
- logger.info("WeixinService doRefund return: {}", refundStr);
- Map<String, String> result = WxPayKit.xmlToMap(refundStr);
- String returnCode = result.get("return_code");
- String returnMsg = result.get("return_msg");
- if (!WxPayKit.codeIsOk(returnCode)) {
- logger.error(returnMsg);
- return false;
- }
- return true;
- } catch (Exception e) {
- throw new BusinessCheckException("WeixinService.doRefund 微信退款失败:" + e.getMessage());
- }
- }
- /**
- * 获取支付配置
- * @param storeId
- * @param platform
- * */
- private WxPayApiConfig getApiConfig(Integer storeId, String platform) throws BusinessCheckException {
- WxPayApiConfig apiConfig;
- MtStore mtStore = storeService.queryStoreById(storeId);
- String mchId = wxPayBean.getMchId();
- String apiV2 = wxPayBean.getApiV2();
- if (mtStore != null && StringUtil.isNotEmpty(mtStore.getWxApiV2()) && StringUtil.isNotEmpty(mtStore.getWxMchId())) {
- mchId = mtStore.getWxMchId();
- apiV2 = mtStore.getWxApiV2();
- }
- apiConfig = WxPayApiConfig.builder()
- .appId(wxPayBean.getAppId())
- .mchId(mchId)
- .partnerKey(apiV2)
- .certPath(wxPayBean.getCertPath())
- .domain(wxPayBean.getDomain())
- .build();
- // 微信内h5公众号支付
- if (platform.equals(PlatformTypeEnum.H5.getCode())) {
- String wxAppId = env.getProperty("weixin.official.appId");
- String wxAppSecret = env.getProperty("weixin.official.appSecret");
- if (StringUtil.isNotEmpty(wxAppId) && StringUtil.isNotEmpty(wxAppSecret)) {
- apiConfig.setAppId(wxAppId);
- apiConfig.setApiKey(wxAppSecret);
- }
- }
- WxPayApiConfigKit.setThreadLocalWxPayApiConfig(apiConfig);
- return apiConfig;
- }
- }
|