公共配置类

import lombok.Data;
import springboot.util.TestProperties;@Data
public class PayConfig {//appId(与你商户号绑定的小程序或公众号的appid)private String appID= "wxzf.appID";//小程序秘钥private String aPPSECRET="wxzf.aPPSECRET";//商户号private String mchID="wxzf.mchID";//支付秘钥private String Key="wxzf.Key";}

支付签名工具

import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
import java.security.MessageDigest;
import java.util.Arrays;
import java.util.Map;
import java.util.Set;/*** 生成签名*/
public class SignUtil {//指定为MD5加密方式public static String generateSignature(Map<String, String> data, String key) throws Exception {return generateSignature(data, key, "MD5");}//自选加密方式加密方式public static String generateSignature(Map<String, String> data, String key, String signType) throws Exception {Set<String> keySet = data.keySet();String[] keyArray = (String[])keySet.toArray(new String[keySet.size()]);Arrays.sort(keyArray);StringBuilder sb = new StringBuilder();String[] var6 = keyArray;int var7 = keyArray.length;for(int var8 = 0; var8 < var7; ++var8) {String k = var6[var8];if (!k.equals("sign") && ((String)data.get(k)).trim().length() > 0) {sb.append(k).append("=").append(((String)data.get(k)).trim()).append("&");}}sb.append("key=").append(key);if ("MD5".equals(signType)) {return MD5(sb.toString()).toUpperCase();} else if ("HMACSHA256".equals(signType)) {return HMACSHA256(sb.toString(), key);} else {throw new Exception(String.format("Invalid sign_type: %s", signType));}}public static String MD5(String data) throws Exception {MessageDigest md = MessageDigest.getInstance("MD5");byte[] array = md.digest(data.getBytes("UTF-8"));StringBuilder sb = new StringBuilder();byte[] var4 = array;int var5 = array.length;for(int var6 = 0; var6 < var5; ++var6) {byte item = var4[var6];sb.append(Integer.toHexString(item & 255 | 256).substring(1, 3));}return sb.toString().toUpperCase();}public static String HMACSHA256(String data, String key) throws Exception {Mac sha256_HMAC = Mac.getInstance("HmacSHA256");SecretKeySpec secret_key = new SecretKeySpec(key.getBytes("UTF-8"), "HmacSHA256");sha256_HMAC.init(secret_key);byte[] array = sha256_HMAC.doFinal(data.getBytes("UTF-8"));StringBuilder sb = new StringBuilder();byte[] var6 = array;int var7 = array.length;for(int var8 = 0; var8 < var7; ++var8) {byte item = var6[var8];sb.append(Integer.toHexString(item & 255 | 256).substring(1, 3));}return sb.toString().toUpperCase();}
}

支付签名验证工具

import springboot.wexPayApi.dto.PayConfig;import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
import java.security.MessageDigest;
import java.util.Arrays;
import java.util.Map;
import java.util.Set;/*** 验证签名*/
public class Verification {public static boolean isPayResultNotifySignatureValid(Map<String, String> reqData) throws Exception {String signTypeInData = (String)reqData.get("sign_type");String signType;if (signTypeInData == null) {signType = "MD5";} else {signTypeInData = signTypeInData.trim();if (signTypeInData.length() == 0) {signType =  "MD5";} else if ("MD5".equals(signTypeInData)) {signType =  "MD5";} else {if (!"HMAC-SHA256".equals(signTypeInData)) {throw new Exception(String.format("Unsupported sign_type: %s", signTypeInData));}signType = "HMACSHA256";}}PayConfig config=new PayConfig();return isSignatureValid(reqData, config.getKey(), signType);}public static boolean isSignatureValid(Map<String, String> data, String key, String signType) throws Exception {if (!data.containsKey("sign")) {return false;} else {String sign = (String)data.get("sign");return generateSignature(data, key, signType).equals(sign);}}public static String generateSignature(Map<String, String> data, String key, String signType) throws Exception {Set<String> keySet = data.keySet();String[] keyArray = (String[])keySet.toArray(new String[keySet.size()]);Arrays.sort(keyArray);StringBuilder sb = new StringBuilder();String[] var6 = keyArray;int var7 = keyArray.length;for(int var8 = 0; var8 < var7; ++var8) {String k = var6[var8];if (!k.equals("sign") && ((String)data.get(k)).trim().length() > 0) {sb.append(k).append("=").append(((String)data.get(k)).trim()).append("&");}}sb.append("key=").append(key);if ("MD5".equals(signType)) {return MD5(sb.toString()).toUpperCase();} else if ("HMACSHA256".equals(signType)) {return HMACSHA256(sb.toString(), key);} else {throw new Exception(String.format("Invalid sign_type: %s", signType));}}public static String HMACSHA256(String data, String key) throws Exception {Mac sha256_HMAC = Mac.getInstance("HmacSHA256");SecretKeySpec secret_key = new SecretKeySpec(key.getBytes("UTF-8"), "HmacSHA256");sha256_HMAC.init(secret_key);byte[] array = sha256_HMAC.doFinal(data.getBytes("UTF-8"));StringBuilder sb = new StringBuilder();byte[] var6 = array;int var7 = array.length;for(int var8 = 0; var8 < var7; ++var8) {byte item = var6[var8];sb.append(Integer.toHexString(item & 255 | 256).substring(1, 3));}return sb.toString().toUpperCase();}public static String MD5(String data) throws Exception {MessageDigest md = MessageDigest.getInstance("MD5");byte[] array = md.digest(data.getBytes("UTF-8"));StringBuilder sb = new StringBuilder();byte[] var4 = array;int var5 = array.length;for(int var6 = 0; var6 < var5; ++var6) {byte item = var4[var6];sb.append(Integer.toHexString(item & 255 | 256).substring(1, 3));}return sb.toString().toUpperCase();}
}

普通请求发送工具post,get请求

import javax.net.ssl.*;
import javax.servlet.http.HttpServletRequest;
import java.io.*;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.security.KeyManagementException;
import java.security.NoSuchAlgorithmException;
import java.security.NoSuchProviderException;
import java.security.SecureRandom;
import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.util.Iterator;
import java.util.Map;/*** 发送请求(post,get请求)*/
public class HttpKit {private static String CHARSET = "UTF-8";private static final SSLSocketFactory sslSocketFactory = initSSLSocketFactory();private static final TrustAnyHostnameVerifier trustAnyHostnameVerifier = new HttpKit().new TrustAnyHostnameVerifier();//    public static final OkHttp3Delegate delegate = new OkHttp3Delegate();private HttpKit() {}private static SSLSocketFactory initSSLSocketFactory() {try {TrustManager[] e = new TrustManager[]{new HttpKit().new TrustAnyTrustManager()};SSLContext sslContext = SSLContext.getInstance("TLS");sslContext.init((KeyManager[])null, e, new SecureRandom());return sslContext.getSocketFactory();} catch (Exception var2) {throw new RuntimeException(var2);}}private static HttpURLConnection getHttpConnection(String url, String method, Map<String, String> headers) throws IOException, NoSuchAlgorithmException, NoSuchProviderException, KeyManagementException{URL _url = new URL(url);HttpURLConnection conn = (HttpURLConnection)_url.openConnection();if(conn instanceof HttpsURLConnection) {((HttpsURLConnection)conn).setSSLSocketFactory(sslSocketFactory);((HttpsURLConnection)conn).setHostnameVerifier(trustAnyHostnameVerifier);}conn.setRequestMethod(method);conn.setDoOutput(true);conn.setDoInput(true);conn.setConnectTimeout(19000);conn.setReadTimeout(19000);conn.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");conn.setRequestProperty("AuthUser-Agent", "Mozilla/5.0 (Windows NT 6.3; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/33.0.1750.146 Safari/537.36");if(headers != null && !headers.isEmpty()) {Iterator i$ = headers.entrySet().iterator();while(i$.hasNext()) {Map.Entry entry = (Map.Entry)i$.next();conn.setRequestProperty((String)entry.getKey(), (String)entry.getValue());}}return conn;}public static String get(String url, Map<String, String> queryParas, Map<String, String> headers) {HttpURLConnection conn = null;String e;try {conn = getHttpConnection(buildUrlWithQueryString(url, queryParas), "GET", headers);conn.connect();e = readResponseString(conn);} catch (Exception var8) {throw new RuntimeException(var8);} finally {if(conn != null) {conn.disconnect();}}return e;}public static String get(String url, Map<String, String> queryParas) {return get(url, queryParas, (Map)null);}public static String get(String url) {return get(url, (Map)null, (Map)null);}public static String post(String url, Map<String, String> queryParas, String data, Map<String, String> headers) {HttpURLConnection conn = null;String var6;try {conn = getHttpConnection(buildUrlWithQueryString(url, queryParas), "POST", headers);conn.connect();OutputStream e = conn.getOutputStream();e.write(data.getBytes(CHARSET));e.flush();e.close();var6 = readResponseString(conn);} catch (Exception var10) {throw new RuntimeException(var10);} finally {if(conn != null) {conn.disconnect();}}return var6;}public static String post(String url, Map<String, String> queryParas, String data) {return post(url, queryParas, data, (Map)null);}public static String post(String url, String data, Map<String, String> headers) {return post(url, (Map)null, data, headers);}public static String post(String url, String data) {return post(url, (Map)null, data, (Map)null);}private static String readResponseString(HttpURLConnection conn) {StringBuilder sb = new StringBuilder();InputStream inputStream = null;try {inputStream = conn.getInputStream();BufferedReader e = new BufferedReader(new InputStreamReader(inputStream, CHARSET));String line = null;while((line = e.readLine()) != null) {sb.append(line).append("\n");}String var5 = sb.toString();return var5;} catch (Exception var14) {throw new RuntimeException(var14);} finally {if(inputStream != null) {try {inputStream.close();} catch (IOException var13) {}}}}private static String buildUrlWithQueryString(String url, Map<String, String> queryParas) {if(queryParas != null && !queryParas.isEmpty()) {StringBuilder sb = new StringBuilder(url);boolean isFirst;if(url.indexOf("?") == -1) {isFirst = true;sb.append("?");} else {isFirst = false;}String key;String value;for(Iterator i$ = queryParas.entrySet().iterator() ; i$.hasNext(); sb.append(key).append("=").append(value)) {Map.Entry entry = (Map.Entry)i$.next();if(isFirst) {isFirst = false;} else {sb.append("&");}key = (String)entry.getKey();value = (String)entry.getValue();if(value!=null && !"".equals(value)) {try {value = URLEncoder.encode(value, CHARSET);} catch (UnsupportedEncodingException var9) {throw new RuntimeException(var9);}}}return sb.toString();} else {return url;}}public static String readData(HttpServletRequest request) {BufferedReader br = null;try {StringBuilder e = new StringBuilder();br = request.getReader();String line = null;while((line = br.readLine()) != null) {e.append(line).append("\n");}line = e.toString();return line;} catch (IOException var12) {throw new RuntimeException(var12);} finally {if(br != null) {try {br.close();} catch (IOException var11) {}}}}/** @deprecated */@Deprecatedpublic static String readIncommingRequestData(HttpServletRequest request) {return readData(request);}private class TrustAnyTrustManager implements X509TrustManager {private TrustAnyTrustManager() {}@Overridepublic X509Certificate[] getAcceptedIssuers() {return null;}@Overridepublic void checkClientTrusted(X509Certificate[] chain, String authType) throws CertificateException{}@Overridepublic void checkServerTrusted(X509Certificate[] chain, String authType) throws CertificateException {}}private class TrustAnyHostnameVerifier implements HostnameVerifier {private TrustAnyHostnameVerifier() {}@Overridepublic boolean verify(String hostname, SSLSession session) {return true;}}
}

携带证书请求与处理Xml格式


import com.google.common.reflect.TypeToken;
import com.google.gson.Gson;
import com.google.gson.JsonSyntaxException;
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.InputStreamEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.ssl.SSLContexts;
import org.springframework.core.io.ClassPathResource;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import springboot.util.TestProperties;import javax.net.ssl.SSLContext;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.security.KeyStore;
import java.util.HashMap;
import java.util.Map;/*** 发送HTTPS的post的请求携带证书请求* xml转map,map转xml**/
public class HttpsPost {/*** 微信下单,map to xml* @param params 参数* @return String*/public static String toXml(Map<String, String> params) {StringBuilder xml = new StringBuilder();xml.append("<xml>");//遍历map获取key与valuefor (Map.Entry<String, String> entry : params.entrySet()) {String key   = entry.getKey();String value = entry.getValue();// 略过空值if (isEmpty(value)){ continue;}xml.append("<").append(key).append(">");xml.append(entry.getValue());xml.append("</").append(key).append(">");}xml.append("</xml>");return xml.toString();}/*** 检测字符串是否为空(null,"","null")** @param s* @return 为空则返回true,不否则返回false*/public static boolean isEmpty(String s) {return s == null || "".equals(s) || "null".equals(s);}/*** String转map* @param str_json* @return*/public static Map<String, String> json2map(String str_json) {Map<String, String> res = null;try {Gson gson = new Gson();res = gson.fromJson(str_json, new TypeToken<Map<String, String>>() {}.getType());} catch (JsonSyntaxException e) {}return res;}/*** 带证书httpPost请求* @param url   接口地址* @param param 参数* @return* @throws Exception*/public static String sendRedEnvelope(String url, String param) throws Exception {//PKCS12的密码String PKCS12 = TestProperties.getvalue("wxzf.mchID");//证书地址 apiclient_cert.p12String fileRoute = TestProperties.getvalue("wxzf.certPath");//指定读取证书格式为PKCS12KeyStore keyStore = KeyStore.getInstance("PKCS12");//读取本机存放的PKCS12证书文件
//        FileInputStream instream = new FileInputStream(new File(fileRoute));InputStream instream = new ClassPathResource(fileRoute).getInputStream();try {//指定PKCS12的密码keyStore.load(instream, PKCS12.toCharArray());} finally {instream.close();}//指定TLS版本SSLContext sslcontext = SSLContexts.custom().loadKeyMaterial(keyStore, PKCS12.toCharArray()).build();//设置httpclient的SSLSocketFactorySSLConnectionSocketFactory sslsf = new SSLConnectionSocketFactory(sslcontext,new String[]{"TLSv1"},null,SSLConnectionSocketFactory.BROWSER_COMPATIBLE_HOSTNAME_VERIFIER);CloseableHttpClient httpclient = HttpClients.custom().setSSLSocketFactory(sslsf).build();StringBuffer stringBuffer = new StringBuffer();try {HttpPost httpPost = new HttpPost(url);InputStream is = new ByteArrayInputStream(param.getBytes("UTF-8"));//InputStreamEntity严格是对内容和长度相匹配的。用法和BasicHttpEntity类似InputStreamEntity inputStreamEntity = new InputStreamEntity(is, is.available());httpPost.setEntity(inputStreamEntity);CloseableHttpResponse response = httpclient.execute(httpPost);try {HttpEntity entity = response.getEntity();BufferedReader reader = new BufferedReader(new InputStreamReader(entity.getContent(), "UTF-8"));String inputLine;while ((inputLine = reader.readLine()) != null) {stringBuffer.append(inputLine);}} finally {response.close();}} finally {httpclient.close();}String str=stringBuffer.toString();return str;}/*** XML格式字符串转换为Map** @param xml XML字符串* @return XML数据转换后的Map* @throws Exception*/public static Map<String, String> xmlToMap(String xml) {try {Map<String, String> data = new HashMap<>();DocumentBuilderFactory documentBuilderFactory = DocumentBuilderFactory.newInstance();DocumentBuilder documentBuilder = documentBuilderFactory.newDocumentBuilder();InputStream stream = new ByteArrayInputStream(xml.getBytes("UTF-8"));org.w3c.dom.Document doc = documentBuilder.parse(stream);doc.getDocumentElement().normalize();NodeList nodeList = doc.getDocumentElement().getChildNodes();for (int idx = 0; idx < nodeList.getLength(); ++idx) {Node node = nodeList.item(idx);if (node.getNodeType() == Node.ELEMENT_NODE) {org.w3c.dom.Element element = (org.w3c.dom.Element) node;data.put(element.getNodeName(), element.getTextContent());}}stream.close();return data;} catch (Exception e) {e.printStackTrace();return null;}}}

Jsapi支付

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;
import springboot.util.startuputil.IpUtil;
import springboot.wexPayApi.controller.HDController;
import springboot.wexPayApi.dto.PayConfig;
import springboot.wexPayApi.util.HttpKit;
import springboot.wexPayApi.util.HttpsPost;
import springboot.wexPayApi.util.SignUtil;import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;/*** Jsapi支付接口* 文档地址:https://pay.weixin.qq.com/wiki/doc/api/jsapi.php?chapter=9_1* 作者:王文斌*/
@Component
public class JsapiPayUtil {private static Logger logger = LoggerFactory.getLogger(HDController.class);//可注释/*** 微信支付接口** @param money  金额* @param openid 用户openid* @return* @throws Exception*/public  Object genWxProgramPayChannel(String money, String orderNumber, String openid, String body) throws Exception {//orderNumber号 订单PayConfig config = new PayConfig();Map<String, String> reqParams = new HashMap<>();//微信分配的小程序IDreqParams.put("appid", config.getAppID());//微信支付分配的商户号reqParams.put("mch_id", config.getMchID());//随机字符串reqParams.put("nonce_str", System.currentTimeMillis() / 1000 + "");//签名类型reqParams.put("sign_type", "MD5");//充值订单 商品描述reqParams.put("body", body);//商户订单号reqParams.put("out_trade_no", orderNumber);//订单总金额,单位为分reqParams.put("total_fee", money);//终端IPreqParams.put("spbill_create_ip", IpUtil.getRequestIp());//通知地址http://www.bskuqi.cn/reqParams.put("notify_url", "https://bskuqi.cn/yldh/web/api/yys/JSAPI/notify/");//交易类型reqParams.put("trade_type", "JSAPI");//用户标识reqParams.put("openid", openid);//签名String sign = SignUtil.generateSignature(reqParams, config.getKey());
//        request.getSession().setAttribute(orderNumber,sign);reqParams.put("sign", sign);/*调用支付定义下单API,返回预付单信息 prepay_id*/String xmlResult = HttpKit.post("https://api.mch.weixin.qq.com/pay/unifiedorder", HttpsPost.toXml(reqParams));logger.info("---" + xmlResult);Map<String, String> result = HttpsPost.xmlToMap(xmlResult);System.out.println("money========================================"+money);String prepay_id = result.get("prepay_id");/*小程序调起支付数据签名*/Map<String, String> packageParams = new HashMap<String, String>();packageParams.put("appId", config.getAppID());packageParams.put("timeStamp", System.currentTimeMillis() / 1000 + "");packageParams.put("nonceStr", System.currentTimeMillis() + "");packageParams.put("package", "prepay_id=" + prepay_id);packageParams.put("signType", "MD5");String packageSign = SignUtil.generateSignature(packageParams, config.getKey());packageParams.put("paySign", packageSign);return packageParams;}/*** jsapi退款方法* @param outTradeNo 退款订单号(支付时产生的订单号)* @param total_fee  总金额(及退款金额)* @return* @throws Exception MD5Util签名异常*/public boolean refund(String outTradeNo, String total_fee) throws Exception {PayConfig config = new PayConfig();Date now = new Date();SimpleDateFormat dateFormat = new SimpleDateFormat("yyyyMMddHHmmss");String hehe = dateFormat.format(now);String out_refund_no = hehe + "wxrefund";int allFee = (int) (Double.parseDouble(total_fee))*100;Map<String, String> reqParams = new HashMap<>();reqParams.put("appid",config.getAppID());reqParams.put("mch_id", config.getMchID());reqParams.put("nonce_str", System.currentTimeMillis() / 1000 + "");reqParams.put("out_trade_no", outTradeNo);reqParams.put("total_fee",String.valueOf(allFee));reqParams.put("refund_fee",String.valueOf(allFee));reqParams.put("out_refund_no",out_refund_no);//签名String sign = SignUtil.generateSignature(reqParams, config.getKey());reqParams.put("sign", sign);System.out.println(HttpsPost.toXml(reqParams));String xmlResult = HttpsPost.sendRedEnvelope("https://api.mch.weixin.qq.com/secapi/pay/refund", HttpsPost.toXml(reqParams));logger.info("---" + xmlResult);Map<String, String> result = HttpsPost.xmlToMap(xmlResult);if(xmlResult.contains("大于可退金额")){return false;}else {return true;}}/*** 退回剩余金额* @param outTradeNo (支付时产生的订单号)* @param all_fee 总金额* @param over_fee 退回金额* @return* @throws Exception*/public boolean overrefund(String outTradeNo, String all_fee,String over_fee) throws Exception {PayConfig config = new PayConfig();System.err.println("进入微信退款申请");Date now = new Date();SimpleDateFormat dateFormat = new SimpleDateFormat("yyyyMMddHHmmss");//可以方便地修改日期格式String hehe = dateFormat.format(now);int allFee = (int) (Double.parseDouble(all_fee))*100; //需要*100int overFee = (int) (Double.parseDouble(over_fee))*100; //需要*100String out_refund_no = hehe + "wxrefund";Map<String, String> reqParams = new HashMap<>();reqParams.put("appid",config.getAppID());reqParams.put("mch_id", config.getMchID());reqParams.put("nonce_str", System.currentTimeMillis() / 1000 + "");reqParams.put("out_trade_no", outTradeNo);reqParams.put("total_fee",String.valueOf(allFee));reqParams.put("refund_fee",String.valueOf(overFee));reqParams.put("out_refund_no",out_refund_no);//签名String sign = SignUtil.generateSignature(reqParams, config.getKey());reqParams.put("sign", sign);System.out.println(HttpsPost.toXml(reqParams));String xmlResult = HttpsPost.sendRedEnvelope("https://api.mch.weixin.qq.com/secapi/pay/refund", HttpsPost.toXml(reqParams));logger.info("---" + xmlResult);Map<String, String> result = HttpsPost.xmlToMap(xmlResult);if(xmlResult.contains("大于可退金额")){return false;}else {return true;}}}

回调

import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import springboot.common.api.ApiResult;
import springboot.common.constant.CommonConstant;
import springboot.wexPayApi.SelectAndCloseUtil;
import springboot.wexPayApi.dto.PayConfig;
import springboot.wexPayApi.util.HttpsPost;
import springboot.wexPayApi.util.Verification;import javax.servlet.http.HttpServletRequest;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.Map;/*** 回调* @Author ttaurus* @Date Create in 2020/1/21 11:24*/
@RestController
@Api(value = CommonConstant.WEB_API_PREFIX + "pay", description = "微信支付")
@RequestMapping(CommonConstant.WEB_API_PREFIX + "/pay")
@Slf4j
public class HDController {//可注释private static Logger logger = LoggerFactory.getLogger(HDController.class);@Autowiredprivate SelectAndCloseUtil selectAndCloseUtil;@PostMapping(value = "/JSAPI/notify/") //回调函数@ApiOperation(value = "添加微信支付回调", notes = "添加微信支付回调", response = ApiResult.class)public String payJSAPI(HttpServletRequest request) {InputStream is = null;String xmlBack = "<xml><return_code><![CDATA[FAIL]]></return_code><return_msg><![CDATA[报文为空]]></return_msg></xml> ";try {is = request.getInputStream();// 将InputStream转换成StringBufferedReader reader = new BufferedReader(new InputStreamReader(is));StringBuilder sb = new StringBuilder();String line = null;while ((line = reader.readLine()) != null) {sb.append(line + "\n");}xmlBack = notify(request, sb.toString());  //调用通知方法System.out.println("返回的信息如下:\n" + sb.toString());System.out.println("已成功支付且回复到微信服务器!");} catch (Exception e) {logger.error("微信手机支付回调通知失败:", e);} finally {if (is != null) {try {is.close();} catch (IOException e) {e.printStackTrace();}}}System.out.println("已成功支付且回复到微信服务器!");return xmlBack;}public String notify(HttpServletRequest request, String notifyStr) {String xmlBack = "<xml><return_code><![CDATA[FAIL]]></return_code><return_msg><![CDATA[报文为空]]></return_msg></xml> ";try {// 转换成map,判断是否是你本商户的支付订单Map<String, String> resultMap = HttpsPost.xmlToMap(notifyStr);if (Verification.isPayResultNotifySignatureValid(resultMap)) {//状态String returnCode = resultMap.get("return_code");String transactionId = resultMap.get("transaction_id");System.out.println(transactionId);if ("SUCCESS".equals(returnCode)) {String outTradeNo = resultMap.get("out_trade_no");//这个if判断是判断该订单是否支付成功,如果支付成功的话就关闭,//都返回Ok就行了不用多此一举做判断了if (selectAndCloseUtil.genSupply(outTradeNo)) {selectAndCloseUtil.CloseSupply(outTradeNo);}//这里写支付完成后的逻辑,你需要更改订单状态之类的东西xmlBack = "<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>";}}} catch (Exception e) {e.printStackTrace();}return xmlBack;}}

springboot对接微信支付相关推荐

  1. SpringBoot对接微信支付之JSAPI

    分享SpringBoot整合微信公众号支付项目,对接微信JSAPI支付类型遇到的问题和过程封装的工具类,目前已正常使用,有问题大家评论区互动哈,有需要源码的可以私信我. 1.创建SpringBoot项 ...

  2. springboot 微信小程序 对接微信支付功能(完整版)

    微信小程序对接微信支付功能 业务流程时序图 JAVA版 1. 项目架构 2. pom.xml配置文件 3. 小程序账号参数配置类 4.JAVA 通用代码 4.1 工具类 4.1.1 IdGen (id ...

  3. SpringBoot对接微信小程序支付功能开发(一,下单功能)

    1,接入前准备: 接入模式选择直连模式: 申请小程序,得到APPID,并开通微信支付: 申请微信商户号,得到mchid,并绑定APPID: 配置商户API key,下载并配置商户证书,根据微信官方文档 ...

  4. SpringBoot对接微信小程序支付功能开发(二,支付回调功能)

    接着上一篇: SpringBoot对接微信小程序支付功能开发(一,下单功能) 在上一篇下单功能中我们有传支付结果回调地址. 下面是回调接口实现 package com.office.miniapp.c ...

  5. 对接微信支付之网页支付详解

    对接微信支付之网页支付详解 声明:转载请注明出处 阅读对象:本文针对的是网页中的扫码支付 温馨提示:微信支付坑比较多,阅读时请仔细一些,不要放过所有需要注意的内容 , 本人一路踩坑过来,希望大家引以为 ...

  6. 简易支付平台(已对接微信支付)

    序 最近H5开发的app需要对接微信支付,我想的是公司貌似开没有支付平台,听说了另一个项目也要对接支付.为了宇宙的和平,我想就提出来单做,所以说干就干,不考虑那么多,只要自己认可自己就行. 一.支付平 ...

  7. Java对接微信支付(完整全流程)

    Java对接微信支付及支付回调通知的全流程 一.所用框架.对接微信支付我们技术组用的是payment框架,因为该框架已整合springboot因此很方便快捷 <dependency>< ...

  8. java对接微信支付收不到支付通知问题(亲身实践)

    问题描述: 用java对接微信支付时,统一下单接口正常.但是用户扫码付款成功后,设置用于回调的notify_url对应的接口并没有收到请求(这个url测试过,是正常的且外网能访问的). 由于官方文档没 ...

  9. node 对接微信支付的踩坑记录(服务端)

    因项目需要,对接了微信支付,微信支付对于网页来说没有什么工作量,申请了商户号后,直接将收款码放到网页上就可以,但是小程序需要调起微信支付直接付款,于是认真翻阅了官网要针对小程序做微信支付的对接. 准备 ...

最新文章

  1. “智源 — INSPEC 工业大数据质量预测赛” 上线,为硬核工业制造炼就 AI 之心...
  2. python 二维数组赋值_python日常注意小知识集锦
  3. layer.js 使用
  4. DL之DCGNN:基于TF利用DCGAN实现在MNIST数据集上训练生成新样本
  5. 日常生活小技巧 -- 文件对比工具 Beyond Compare
  6. 最短路问题之Bellman-ford算法
  7. linux共享内存变量 tiaojianbianliang,修改linux共享内存大小
  8. 关于input单选框的radio属性
  9. 恒位油杯故障原因_抽油烟机常见故障及处理方法
  10. 济宁市机器人科技乐园_人工智能的“游乐场”,邀你免费畅玩!
  11. 聊天机器人语料批量处理-自动提取关键词并自动写入文件
  12. Android之USB打印
  13. pfamscan 的使用_48个在线分析使用工具
  14. 数据库原理第一章测验(标黑的为答案)
  15. ::before 和:before 区别
  16. ps aux含义linux,Linux下ps aux解释
  17. 不要轻易当舔狗,除非你想当技术型舔狗
  18. 抖音新作品发布监控提醒
  19. 8.linux 重定向详解,标准输入输出,输入重定向,输出重定向
  20. 表格实现每行一种颜色

热门文章

  1. 抽丝剥茧——调停者和门面设计模式
  2. 蓝桥杯 分割项链 Java
  3. 用python的gui界面设计签名_Python GUI Tkinter简单实现个性签名设计
  4. 题目:中国有句俗话叫“三天打渔,两天晒网”,某人从2010年1月1日期开始“三天打渔,两天晒网” 问这个人在以后的某一天是“打渔”还是“晒网”。用C或着C++语言实现程序解决问题。
  5. 2021计算机保研面试题目(纯干货)
  6. 微信开发实战(2)—微信公众平台接口调试工具
  7. Docker 镜像,基于 alpine 系统的时区配置
  8. 地图网站显示实时交通路况信息的原理
  9. 2019年东北大学计算机系提档线,东北大学2019年部分省、批次、科类录取分数线发布!...
  10. C语言小项目 扫雷游戏