logo资料库

SpringBoot 微信退款功能的示例代码.pdf

第1页 / 共4页
第2页 / 共4页
第3页 / 共4页
第4页 / 共4页
资料共4页,全文预览结束
SpringBoot 微信退款功能的示例代码 微信退款功能的示例代码 主要介绍了SpringBoot 微信退款功能的实现,本文通过实例代码给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的 朋友可以参考下 一:微信支付证书配置 一:微信支付证书配置 二:证书读取以及读取后的使用 二:证书读取以及读取后的使用 package com.zhx.guides.assistant.config.wechatpay; import org.apache.commons.io.IOUtils; import org.apache.http.HttpEntity; import org.apache.http.client.methods.CloseableHttpResponse; import org.apache.http.client.methods.HttpPost; import org.apache.http.conn.ssl.SSLConnectionSocketFactory; import org.apache.http.entity.StringEntity; import org.apache.http.impl.client.CloseableHttpClient; import org.apache.http.impl.client.HttpClients; import org.apache.http.ssl.SSLContexts; import org.apache.http.util.EntityUtils; import org.springframework.core.io.ClassPathResource; import javax.net.ssl.SSLContext; import java.io.ByteArrayInputStream; import java.io.IOException; import java.io.InputStream; import java.security.KeyStore; /** * @Class WeChatConfigUtil * @Version 1.0 * @Date 创建时间:2020-06-15 16:19 * @Copyright Copyright by * @Direction 类说明 */ public class WeChatConfigUtil { private static byte[] certData; /**** * @throws Exception */ static { try { //从微信商户平台下载的安全证书存放的目录 //String certPath = "D:\\config\\apiclient_cert.p12"; //File file = new File(certPath); //InputStream certStream = new FileInputStream(file); //使用springboot配置文件内读取的方式 ClassPathResource classPathResource = new ClassPathResource("\\user_key\\apiclient_cert.p12"); InputStream certStream = classPathResource.getInputStream(); WeChatConfigUtil.certData = IOUtils.toByteArray(certStream); certStream.read(WeChatConfigUtil.certData); certStream.close(); } catch (IOException e) { e.printStackTrace(); } } /** * 开始退款操作 * * @param mchId 商户ID * @param url 请求URL * @param data 退款参数 * @return * @throws Exception */ public static String doRefund(String mchId, String url, String data) throws Exception { /** * 注意PKCS12证书 是从微信商户平台-》账户设置-》 API安全 中下载的 */ KeyStore keyStore = KeyStore.getInstance("PKCS12"); //这里自行实现我是使用数据库配置将证书上传到了服务器可以使用 FileInputStream读取本地文件 //ByteArrayInputStream inputStream = FileUtil.getInputStream("https://############################.p12"); ByteArrayInputStream inputStream = new ByteArrayInputStream(WeChatConfigUtil.certData); try { //这里写密码..默认是你的MCHID keyStore.load(inputStream, mchId.toCharArray()); } finally { inputStream.close(); } SSLContext sslcontext = SSLContexts.custom() //这里也是写密码的
.loadKeyMaterial(keyStore, mchId.toCharArray()) .build(); SSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory( sslcontext, SSLConnectionSocketFactory.getDefaultHostnameVerifier()); CloseableHttpClient httpclient = HttpClients.custom() .setSSLSocketFactory(sslsf) .build(); try { HttpPost httpost = new HttpPost(url); httpost.setEntity(new StringEntity(data, "UTF-8")); CloseableHttpResponse response = httpclient.execute(httpost); try { HttpEntity entity = response.getEntity(); //接受到返回信息 String jsonStr = EntityUtils.toString(response.getEntity(), "UTF-8"); EntityUtils.consume(entity); return jsonStr; } finally { response.close(); } } finally { httpclient.close(); } } } 三:发起订单退款操作 三:发起订单退款操作 /** * 封装查询请求数据 * @param tradeRefund 退款订单请求信息 * @param path 数据访问PATH * @return */ private static SortedMap refundData( TradeRefund tradeRefund , String path ) throws Exception { //构建参数 Map dataMap = new HashMap<>(); dataMap.put("appid","wx#################"); dataMap.put("mch_id","137#############"); //自行实现该随机串 dataMap.put("nonce_str",Core.MD5("12344")); dataMap.put("out_trade_no","P190808170038402889c5318502"); dataMap.put("out_refund_no","P190808170038402889c5318502"); dataMap.put("total_fee","1"); dataMap.put("refund_fee","1"); dataMap.put("refund_desc","退款"); //生成签名 String sign = PayToolUtil.createSign("UTF-8", dataMap , WeichatPayConfigure.API_KEY ); //WXPayUtil.generateSignature(dataMap, "rv4###################"); dataMap.put("sign", sign); //map数据转xml String requestXML = getRequestXml( dataMap ); logger.info( "订单退款请求参数:\n" + requestXML ); //发起退款 String responseXml = WeChatConfigUtil.doRefund( WeichatPayConfigure.MCH_ID , "https://api.mch.weixin.qq.com/secapi/pay/refund", requestXML ); } /** * @author * @date 2016-4-22 * @Description:将请求参数转换为xml格式的string * @param parameters * 请求参数 * @return */ public static String getRequestXml(SortedMap parameters) { StringBuffer sb = new StringBuffer(); sb.append(""); Set es = parameters.entrySet(); Iterator it = es.iterator(); while (it.hasNext()) { Map.Entry entry = (Map.Entry) it.next(); String k = (String) entry.getKey(); String v = (String) entry.getValue(); if ("attach".equalsIgnoreCase(k) || "body".equalsIgnoreCase(k) || "sign".equalsIgnoreCase(k)) { sb.append("<" + k + ">" + ""); } else { sb.append("<" + k + ">" + v + ""); } } sb.append(""); return sb.toString(); } /** * @author * @date 2016-4-22 * @Description:sign签名 * @param characterEncoding * 编码格式 * @param packageParams * 请求参数 * @return */ public static String createSign(String characterEncoding, SortedMap packageParams, String API_KEY) { StringBuffer sb = new StringBuffer(); Set es = packageParams.entrySet(); Iterator it = es.iterator(); while (it.hasNext()) { Map.Entry entry = (Map.Entry) it.next(); String k = (String) entry.getKey(); String v = (String) entry.getValue();
if (null != v && !"".equals(v) && !"sign".equals(k) && !"key".equals(k)) { sb.append(k + "=" + v + "&"); } } sb.append("key=" + API_KEY); String sign = MD5Util.MD5Encode(sb.toString(), characterEncoding).toUpperCase(); return sign; } package com.zhx.guides.assistant.interfaces.pay.wechatpay.util; import java.security.MessageDigest; public class MD5Util { private static String byteArrayToHexString(byte b[]) { StringBuffer resultSb = new StringBuffer(); for (int i = 0; i < b.length; i++) resultSb.append(byteToHexString(b[i])); return resultSb.toString(); } private static String byteToHexString(byte b) { int n = b; if (n < 0) n += 256; int d1 = n / 16; int d2 = n % 16; return hexDigits[d1] + hexDigits[d2]; } public static String MD5Encode(String origin, String charsetname) { String resultString = null; try { resultString = new String(origin); MessageDigest md = MessageDigest.getInstance("MD5"); if (charsetname == null || "".equals(charsetname)) resultString = byteArrayToHexString(md.digest(resultString .getBytes())); else resultString = byteArrayToHexString(md.digest(resultString .getBytes(charsetname))); } catch (Exception exception) { } return resultString; } /*** * 简化版本 * @param s * @return */ public final static String MD5(String s) { char hexDigits[] = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' }; try { byte[] btInput = s.getBytes("utf-8"); // 获得MD5摘要算法的 MessageDigest 对象 MessageDigest mdInst = MessageDigest.getInstance("MD5"); // 使用指定的字节更新摘要 mdInst.update(btInput); // 获得密文 byte[] md = mdInst.digest(); // 把密文转换成十六进制的字符串形式 int j = md.length; char str[] = new char[j * 2]; int k = 0; for (int i = 0; i < j; i++) { byte byte0 = md[i]; str[k++] = hexDigits[byte0 >>> 4 & 0xf]; str[k++] = hexDigits[byte0 & 0xf]; } return new String(str); } catch (Exception e) { e.printStackTrace(); return null; } } private static final String hexDigits[] = { "0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "a", "b", "c", "d", "e", "f" }; } /** * @author * @date 2016-4-22 * @Description:将请求参数转换为xml格式的string * @param parameters * 请求参数 * @return */ public static String getRequestXml(SortedMap parameters) { StringBuffer sb = new StringBuffer(); sb.append(""); Set es = parameters.entrySet(); Iterator it = es.iterator(); while (it.hasNext()) { Map.Entry entry = (Map.Entry) it.next(); String k = (String) entry.getKey(); String v = (String) entry.getValue(); if ("attach".equalsIgnoreCase(k) || "body".equalsIgnoreCase(k) || "sign".equalsIgnoreCase(k)) { sb.append("<" + k + ">" + ""); } else { sb.append("<" + k + ">" + v + "");
} } sb.append(""); return sb.toString(); } 四:请求XML示例示例 四:请求 wx2421b1c4370ec43b 10000100 6cefdb308e1e2e8aabd48cf79e546a02 1415701182 1415757673 1 1 FE56DD4AA85C0EECA82C35595A69E153 五:官方信息 五:官方信息 官方地址:https://pay.weixin.qq.com/wiki/doc/api/wxa/wxa_api.php?chapter=9_4 需注意这两个参数我使用的是out_trade_no 总结总结 到此这篇关于SpringBoot 微信退款功能的示例代码的文章就介绍到这了,更多相关SpringBoot 微信退款内容请搜索我们以前的文章或继续浏览下面的相关文章希望 大家以后多多支持我们!
分享到:
收藏