微信:linweikun8023 欢迎咨询 记得备注
package cn.com.yyg.front.utils;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import com.qq.connect.utils.json.JSONObject;
public class WeixinAccessToken {
private static Logger logger = LoggerFactory.getLogger(WeixinAccessToken.class);
public static String getAccessToken() {
String access_token = ""; // 有效期为7200秒
String url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=" + WeixinUtils.app_ID + "&secret=" + WeixinUtils.app_Secret;
try {
URL urlGet = new URL(url);
HttpURLConnection http = (HttpURLConnection) urlGet.openConnection();
http.setRequestMethod("GET"); // 必须是get方式请求
http.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
http.setDoOutput(true);
http.setDoInput(true);
System.setProperty("sun.net.client.defaultConnectTimeout", "30000");// 连接超时30秒
System.setProperty("sun.net.client.defaultReadTimeout", "30000"); // 读取超时30秒
http.connect();
InputStream is = http.getInputStream();
int size = is.available();
byte[] jsonBytes = new byte[size];
is.read(jsonBytes);
String message = new String(jsonBytes, "UTF-8");
JSONObject demoJson = new JSONObject(message);
access_token = demoJson.getString("access_token");
logger.info("access_token"+access_token);
System.out.println("access_token"+access_token);
is.close();
} catch (Exception e) {
e.printStackTrace();
}
return access_token;
}
}
package cn.com.yyg.front.utils;
import java.io.UnsupportedEncodingException;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Formatter;
import java.util.HashMap;
import java.util.Map;
import java.util.UUID;
import org.apache.commons.lang3.StringUtils;
public class WeixinSign {
public static void main(String[] args) {
String jsapi_ticket = "jsapi_ticket";
// 注意 URL 一定要动态获取,不能 hardcode
String url = "http://example.com";
Map<String, String> ret = sign(jsapi_ticket, url);
for (Map.Entry entry : ret.entrySet()) {
System.out.println(entry.getKey() + ", " + entry.getValue());
}
};
public static Map<String, String> sign(String jsapi_ticket, String url) {
Map<String, String> ret = new HashMap<String, String>();
String nonce_str = create_nonce_str();
String timestamp = create_timestamp();
String string1;
String signature = "";
// 注意这里参数名必须全部小写,且必须有序
string1 = "jsapi_ticket=" + jsapi_ticket + "&noncestr=" + nonce_str + "×tamp=" + timestamp + "&url=" + url;
// System.out.println(string1);
try {
MessageDigest crypt = MessageDigest.getInstance("SHA-1");
crypt.reset();
crypt.update(string1.getBytes("UTF-8"));
signature = byteToHex(crypt.digest());
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
ret.put("url", url);
ret.put("jsapi_ticket", jsapi_ticket);
ret.put("nonceStr", nonce_str);
ret.put("timestamp", timestamp);
ret.put("signature", signature);
return ret;
}
private static String byteToHex(final byte[] hash) {
Formatter formatter = new Formatter();
for (byte b : hash) {
formatter.format("%02x", b);
}
String result = formatter.toString();
formatter.close();
return result;
}
public static String create_nonce_str() {
return UUID.randomUUID().toString();
}
public static String create_32nonce_str() {
return StringUtils.substring(UUID.randomUUID().toString(), 1, 32);
}
public static String create_timestamp() {
return Long.toString(System.currentTimeMillis() / 1000);
}
}
package cn.com.yyg.front.utils;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import cn.com.yyg.front.web.wap.controller.WapWxPayController;
import com.qq.connect.utils.json.JSONObject;
public class WeixinTicket {
private static Logger logger = LoggerFactory.getLogger(WeixinTicket.class);
public static String getTicket() {
String ticket = null;
String access_token = WeixinUtils.getAccessToken(); // 有效期为7200秒
String url = "https://api.weixin.qq.com/cgi-bin/ticket/getticket?access_token=" + access_token + "&type=jsapi";
try {
URL urlGet = new URL(url);
HttpURLConnection http = (HttpURLConnection) urlGet.openConnection();
http.setRequestMethod("GET"); // 必须是get方式请求
http.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
http.setDoOutput(true);
http.setDoInput(true);
System.setProperty("sun.net.client.defaultConnectTimeout", "30000");// 连接超时30秒
System.setProperty("sun.net.client.defaultReadTimeout", "30000"); // 读取超时30秒
http.connect();
InputStream is = http.getInputStream();
int size = is.available();
byte[] jsonBytes = new byte[size];
is.read(jsonBytes);
String message = new String(jsonBytes, "UTF-8");
JSONObject demoJson = new JSONObject(message);
ticket = demoJson.getString("ticket");
logger.info("ticket="+ticket);
System.out.println("ticket="+ticket);
is.close();
} catch (Exception e) {
e.printStackTrace();
}
return ticket;
}
}
package cn.com.yyg.front.utils;
import java.util.Map;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.ui.ModelMap;
import cn.com.easy.utils.HttpUtils;
import cn.com.yyg.front.dto.WeixinDto;
import com.github.sd4324530.fastweixin.exception.WeixinException;
import com.qq.connect.utils.json.JSONException;
import com.qq.connect.utils.json.JSONObject;
public class WeixinUtils {
// https://mp.weixin.qq.com/wiki/17/c0f37d5704f0b64713d5d2c37b468d75.html
private static Logger logger = LoggerFactory.getLogger(WeixinUtils.class);
public static String app_ID = "";
public static String app_Secret = "";
public static String domailString = "http://5555";
/**
* 获取code 访问到主页 判断获取到code 再去获取用户accessToken
*
* @author linwk 2016年10月13日
*/
public static String getCode() {
String url = "https://open.weixin.qq.com/connect/oauth2/authorize?appid=" + app_ID + "&redirect_uri=" + domailString
+ "&response_type=code&scope=snsapi_userinfo&state=STATE#wechat_redirect";
return "redirect:" + url;
}
/**
* 获取用户openId 用户accessToken
*
* @return
* @author linwk 2016年10月13日
* @throws Exception
*/
public static String getOpenIdAndAccessToken(String code) throws Exception {
try {
logger.info("code=" + code);
String url = "https://api.weixin.qq.com/sns/oauth2/access_token?appid=" + app_ID + "&secret=" + app_Secret + "&code=" + code + "&grant_type=authorization_code";
String accrssString = HttpUtils.doGet(url);
logger.info("access_token=" + accrssString);
return accrssString;
} catch (WeixinException e) {
logger.info("code=" + code);
String url = "https://api.weixin.qq.com/sns/oauth2/access_token?appid=" + app_ID + "&secret=" + app_Secret + "&code=" + code + "&grant_type=authorization_code";
String accrssString = HttpUtils.doGet(url);
logger.info("access_token=" + accrssString);
return accrssString;
}
}
/**
* 获取用户openId 用户accessToken
*
* @return
* @author linwk 2016年10月13日
* @throws Exception
*/
public static String getUserInfo(String openid, String access_token) throws Exception {
try {
logger.info("openid=" + openid + "*************************** access_token=" + access_token);
String url = "https://api.weixin.qq.com/sns/userinfo?access_token=" + access_token + "&openid=" + openid + "&lang=zh_CN";
String UserInfo = HttpUtils.doGet(url);
logger.info("UserInfo=" + UserInfo);
return UserInfo;
} catch (WeixinException e) {
logger.info("openid=" + openid + "*************************** access_token=" + access_token);
String url = "https://api.weixin.qq.com/sns/userinfo?access_token=" + access_token + "&openid=" + openid + "&lang=zh_CN";
String UserInfo = HttpUtils.doGet(url);
logger.info("UserInfo=" + UserInfo);
return UserInfo;
}
}
/**
* 微信登录验证
*
* @param request
* @param response
* @author linwk 2016年6月15日
* @throws Exception
*/
public static WeixinDto doPost(HttpServletRequest request, HttpServletResponse response, String code) throws Exception {
try {
response.setContentType("text/html; charset=utf-8");
// 获取用户openId 用户accessToken
String accrssString = getOpenIdAndAccessToken(code);
if (StringUtils.isNoneBlank(accrssString)) {
logger.info("获取***************************openid*************************************信息成功");
JSONObject demoJson = new JSONObject(accrssString);
String openid = getJsonName(demoJson, "openid");
String access_token = getJsonName(demoJson, "access_token");
String UserInfo = getUserInfo(openid, access_token);
if (StringUtils.isNoneBlank(UserInfo)) {
logger.info("获取***************************openid*************************************信息成功");
JSONObject UserInfoJson = new JSONObject(UserInfo);
String nickname = getJsonName(UserInfoJson, "nickname");
String sex = getJsonName(UserInfoJson, "sex");
String headimgurl = getJsonName(UserInfoJson, "headimgurl");
WeixinDto weixin = new WeixinDto(openid, nickname, sex, headimgurl);
return weixin;
}
}
} catch (WeixinException e) {
}
return null;
}
private static String getJsonName(JSONObject demoJson, String tString) throws JSONException {
return demoJson.getString(tString);
}
/**
* 微信浏览器判读
*
* @param req
* @author linwk 2016年10月17日
* @param modelMap
*/
public static void extracted(HttpServletRequest request) {
String ua = ((HttpServletRequest) request).getHeader("user-agent").toLowerCase();
if (ua.indexOf("micromessenger") > 0) {// 是微信浏览器
// [微信登录脚本]
request.getSession().setAttribute("isWeixinBrowerisWeixinBrower", true);
request.getSession().setAttribute("isWeixinBrower", true);
request.getSession().setAttribute("appId", WeixinUtils.app_ID);
String jsapi_ticket = WeixinUtils.getTicket();
// 注意 URL 一定要动态获取,不能 hardcode
String url = RequestUtils.getUrl(request);
Map<String, String> ret = WeixinSign.sign(jsapi_ticket, url);
for (@SuppressWarnings("rawtypes")
Map.Entry entry : ret.entrySet()) {
request.getSession().setAttribute(entry.getKey().toString(), entry.getValue());
}
}
}
/**
* get accessToken
*
* @return
* @author linwk 2016年10月13日
*/
public static String getAccessToken() {
if (StringUtils.isBlank(System.getProperty("accessToken"))) {
System.setProperty("accessToken", WeixinAccessToken.getAccessToken());
}
return System.getProperty("accessToken");
}
/**
* set accessToken
*
* @param accessToken
* @author linwk 2016年10月13日
*/
public static void setAccessToken(String accessToken) {
System.setProperty("accessToken", accessToken);
}
/**
* get ticket
*
* @return
* @author linwk 2016年10月13日
*/
public static String getTicket() {
if (StringUtils.isBlank(System.getProperty("ticket"))) {
System.setProperty("ticket", WeixinTicket.getTicket());
}
return System.getProperty("ticket");
}
/**
* set ticket
*
* @param ticket
* @author linwk 2016年10月13日
*/
public static void setTicket(String ticket) {
System.setProperty("ticket", ticket);
}
}
package cn.com.yyg.pay.util;
import java.io.UnsupportedEncodingException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;
import java.util.SortedMap;
import java.util.TreeMap;
import org.apache.commons.codec.digest.DigestUtils;
import cn.com.yyg.front.utils.WeixinSign;
import cn.com.yyg.front.utils.WeixinUtils;
import cn.com.yyg.pay.wxpay.sdk.HttpUtil;
import cn.com.yyg.pay.wxpay.sdk.MD5Util;
import cn.com.yyg.pay.wxpay.sdk.XMLUtil;
/**
* 微信支付
*
* @author lvzf 2016年9月28日
*
*/
public class WxPayUtil {
static String UFDODER_URL = "https://api.mch.weixin.qq.com/pay/unifiedorder";
/**
* 生成h5支付连接
*
* @param appId
* @param appKey
* @param merId
* @param orderId
* @param amount
* @param notifyUrl
* @param ip
* @return
* @throws Exception
* @author linwk 2016年10月10日
* @param openId
*/
@SuppressWarnings({ "unchecked", "rawtypes" })
public static Map getWeixinPayMap(String appId, String appKey, String merId, String orderId, String amount, String notifyUrl, String ip, String openId, String timeStamp)
throws Exception {
// String appsecret = PayConfigUtil.APP_SECRET; // appsecret
String currTime = getCurrTime();
String strTime = currTime.substring(8, currTime.length());
String strRandom = buildRandom(4) + "";
String nonce_str = strTime + strRandom;
// 价格 注意:价格的单位是分
amount = String.valueOf((long) (Double.parseDouble(amount) * 100));
String body = "商品名称"; // 商品名称
String trade_type = "JSAPI";
SortedMap<Object, Object> packageParams = new TreeMap<Object, Object>();
packageParams.put("appid", appId);
packageParams.put("mch_id", merId);
packageParams.put("nonce_str", nonce_str);
packageParams.put("body", body);
packageParams.put("device_info", "WEB");
if (openId != null) {
packageParams.put("openid", openId);
}
packageParams.put("product_id", orderId);
// 订单号
packageParams.put("out_trade_no", orderId);
packageParams.put("total_fee", amount);
// 获取发起电脑 ip
packageParams.put("spbill_create_ip", ip);
// 回调接口
packageParams.put("notify_url", notifyUrl);
packageParams.put("trade_type", trade_type);
String sign = createSign("UTF-8", packageParams, appKey);
packageParams.put("sign", sign);
String requestXML = getRequestXml(packageParams);
System.out.println("请求:" + requestXML);
String resXml = HttpUtil.postData(UFDODER_URL, requestXML);
System.out.println("响应:" + resXml);
Map map = XMLUtil.doXMLParse(resXml);
SortedMap<Object, Object> packagePayParams = new TreeMap<Object, Object>();
packagePayParams.put("appId", appId);
packagePayParams.put("timeStamp", timeStamp);
packagePayParams.put("nonceStr", (String) map.get("nonce_str"));
packagePayParams.put("package", "prepay_id=" + (String) map.get("prepay_id"));
packagePayParams.put("signType", "MD5");
// 再次签名
String paySign = createSign("UTF-8", packagePayParams, appKey);
map.put("paySign", paySign);
//map.put("nonceStr", (String) map.get("nonce_str"));
return map;
}
/**
* 生成支付二维码
*
* @param appId
* @param appKey
* @param merId
* 商户号
* @param orderId
* 订单号
* @param amount
* 金额(元)
* @param notifyUrl
* @param ip
* @return
* @throws Exception
* @author lvzf 2016年9月26日
*/
public static String createQrcode(String appId, String appKey, String merId, String orderId, String amount, String notifyUrl, String ip) throws Exception {
// String appsecret = PayConfigUtil.APP_SECRET; // appsecret
String currTime = getCurrTime();
String strTime = currTime.substring(8, currTime.length());
String strRandom = buildRandom(4) + "";
String nonce_str = strTime + strRandom;
// 价格 注意:价格的单位是分
amount = String.valueOf((long) (Double.parseDouble(amount) * 100));
String body = "扫描付款"; // 商品名称
String trade_type = "NATIVE";
SortedMap<Object, Object> packageParams = new TreeMap<Object, Object>();
packageParams.put("appid", appId);
packageParams.put("mch_id", merId);
packageParams.put("nonce_str", nonce_str);
packageParams.put("body", body);
packageParams.put("device_info", "web");
packageParams.put("product_id", orderId);
// 订单号
packageParams.put("out_trade_no", orderId);
packageParams.put("total_fee", amount);
// 获取发起电脑 ip
packageParams.put("spbill_create_ip", ip);
// 回调接口
packageParams.put("notify_url", notifyUrl);
packageParams.put("trade_type", trade_type);
String sign = createSign("UTF-8", packageParams, appKey);
packageParams.put("sign", sign);
String requestXML = getRequestXml(packageParams);
System.out.println("请求:" + requestXML);
String resXml = HttpUtil.postData(UFDODER_URL, requestXML);
System.out.println("响应:" + resXml);
@SuppressWarnings("rawtypes")
Map map = XMLUtil.doXMLParse(resXml);
@SuppressWarnings("unused")
String return_code = (String) map.get("return_code");
String prepay_id = (String) map.get("prepay_id");
@SuppressWarnings("unused")
String urlCode = (String) map.get("code_url");
sign = (String) map.get("sign");
return urlCode;
}
/**
* 是否签名正确,规则是:按参数名称a-z排序,遇到空值的参数不参加签名。
*
* @return boolean
*/
@SuppressWarnings("rawtypes")
public static boolean isTenpaySign(String characterEncoding, SortedMap<Object, Object> 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 (!"sign".equals(k) && null != v && !"".equals(v)) {
sb.append(k + "=" + v + "&");
}
}
sb.append("key=" + API_KEY);
// 算出摘要
String mysign = MD5Util.MD5Encode(sb.toString(), characterEncoding).toLowerCase();
String tenpaySign = ((String) packageParams.get("sign")).toLowerCase();
// System.out.println(tenpaySign + " " + mysign);
return tenpaySign.equals(mysign);
}
/**
*
* @param map
* @return
* @author linwk 2016年10月18日
*/
private static String getSign(Map<String, String> map) {
StringBuffer sb = new StringBuffer();
@SuppressWarnings("rawtypes")
Set es = map.entrySet();// 所有参与传参的参数按照accsii排序(升序)
@SuppressWarnings("rawtypes")
Iterator it = es.iterator();
while (it.hasNext()) {
@SuppressWarnings("rawtypes")
Map.Entry entry = (Map.Entry) it.next();
String k = (String) entry.getKey();
Object v = entry.getValue();
if (null != v && !"".equals(v) && !"sign".equals(k) && !"key".equals(k)) {
sb.append(k + "=" + v + "&");
}
}
// 你在公众号内设置的密钥
sb.append("key=" + WeixinUtils.app_Secret);
// MD5加密方法,文章后面会提供工具类下载
String sign = DigestUtils.md5Hex(getContentBytes(sb.toString(), "UTF-8")).toUpperCase();
return sign;
}
/**
* @author
* @date 2016-4-22
* @Description:sign签名
* @param characterEncoding
* 编码格式
* @param parameters
* 请求参数
* @return
*/
@SuppressWarnings("rawtypes")
public static String createSign(String characterEncoding, SortedMap<Object, Object> 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();
String sign = DigestUtils.md5Hex(getContentBytes(sb.toString(), characterEncoding)).toUpperCase();
return sign;
}
private static byte[] getContentBytes(String content, String charset) {
if (charset == null || "".equals(charset)) {
return content.getBytes();
}
try {
return content.getBytes(charset);
} catch (UnsupportedEncodingException e) {
throw new RuntimeException("MD5签名过程中出现错误,指定的编码集不对,您目前指定的编码集是:" + charset);
}
}
/**
* @author
* @date 2016-4-22
* @Description:将请求参数转换为xml格式的string
* @param parameters
* 请求参数
* @return
*/
@SuppressWarnings("rawtypes")
public static String getRequestXml(SortedMap<Object, Object> parameters) {
StringBuffer sb = new StringBuffer();
sb.append("<xml>");
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)) {
if ("attach".equalsIgnoreCase(k)) {
sb.append("<" + k + ">" + "<![CDATA[" + v + "]]></" + k + ">");
} else {
sb.append("<" + k + ">" + v + "</" + k + ">");
}
}
sb.append("</xml>");
return sb.toString();
}
/**
* 取出一个指定长度大小的随机正整数.
*
* @param length
* int 设定所取出随机数的长度。length小于11
* @return int 返回生成的随机数。
*/
public static int buildRandom(int length) {
int num = 1;
double random = Math.random();
if (random < 0.1) {
random = random + 0.1;
}
for (int i = 0; i < length; i++) {
num = num * 10;
}
return (int) ((random * num));
}
/**
* 获取当前时间 yyyyMMddHHmmss
*
* @return String
*/
public static String getCurrTime() {
Date now = new Date();
SimpleDateFormat outFormat = new SimpleDateFormat("yyyyMMddHHmmss");
String s = outFormat.format(now);
return s;
}
public static void main(String[] args) {
String merId = "1388261002";
String appId = "wxe913ec262d781dca";
String appKey = "c80f86302e55cdbcb6fae727991ff4c6";
String orderId = "" + System.currentTimeMillis();
String amount = "0.02";
String openId = "oPgBSwL8NcYm5XdZH3rBSxClYUzY";
try {
// String url = WxPayUtil.createQrcode(appId, appKey, merId,
// orderId, amount, "http://www.qibao99.com/wxPay/smBack/",
// "123.12.12.123");
// System.out.println("url=" + url);
// QRCodeImgUtils.createImg(url, 300, 300, "D:/newPic.jpg");
@SuppressWarnings("unchecked")
Map<String, String> map = WxPayUtil.getWeixinPayMap(appId, appKey, merId, orderId, amount, "http://www.qibao99.com/wxPay/smBack/", "123.12.12.123", openId,
WeixinSign.create_timestamp());
for (@SuppressWarnings("rawtypes")
Map.Entry entry : map.entrySet()) {
System.out.println("key:" + entry.getKey().toString() + ",value:" + entry.getValue());
}
} catch (Exception e) {
e.printStackTrace();
}
}
}
package cn.com.yyg.front.web.wap.controller;
import java.io.BufferedOutputStream;
import java.io.BufferedReader;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.Date;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.SortedMap;
import java.util.TreeMap;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.commons.lang.StringUtils;
import org.apache.commons.lang.math.NumberUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.RequestMapping;
import cn.com.easy.exception.BusinessException;
import cn.com.easy.utils.FastJSONUtils;
import cn.com.easy.utils.IPUtils;
import cn.com.yyg.base.entity.PayRecordEntity;
import cn.com.yyg.base.entity.UserEntity;
import cn.com.yyg.front.dao.UserDao;
import cn.com.yyg.front.service.PayService;
import cn.com.yyg.front.service.YgBuyService;
import cn.com.yyg.front.utils.RequestUtils;
import cn.com.yyg.front.utils.WeixinSign;
import cn.com.yyg.pay.util.WxPayUtil;
import cn.com.yyg.pay.wxpay.sdk.XMLUtil;
/**
* 微信扫描支付
*
* @author lvzf 2016年8月30日
*
*/
@Controller
@RequestMapping("/wap/wxPay")
public class WapWxPayController {
private Logger logger = LoggerFactory.getLogger(WapWxPayController.class);
@Autowired
private UserDao userDao;
@Autowired
private YgBuyService ygBuyService;
@Autowired
private PayService payService;
// 商户号
String merId = "";
// 应用id
String appId = "";
// 应用秘钥
String appKey = "";
/**
* 微信支付页面
*
* @param modelMap
* @param req
* @param res
* @param payNo
* @return
* @author linwk 2016年10月17日
*/
@RequestMapping
public String pay(ModelMap modelMap, HttpServletRequest req, HttpServletResponse res, String payNo) {
// 参数设置
try {
req.getSession().setAttribute("isWeixinBrowerisWeixinBrower", false);
req.getSession().setAttribute("isWeixinBrower", false);
PayRecordEntity pay = payService.getPayByPayNo(payNo);
if (pay == null || pay.getPayStatus() != PayRecordEntity.PAY_STATUS_INIT) {
throw new BusinessException("该订单已经支付或取消");
}
String payAmount = pay.getAmount().toString();
if (NumberUtils.isNumber(payAmount) == false) {
throw new BusinessException("请输入数字");
}
if (Double.parseDouble(payAmount) < 0.01) {
throw new BusinessException("金额大于0.01元");
}
String orderId = payNo;
String serverPort = "";
if (req.getServerPort() != 80) {
serverPort = ":" + req.getServerPort();
}
String contextPath = req.getContextPath();
if (contextPath == "/") {
contextPath = "";
}
String path = req.getScheme() + "://" + req.getServerName() + serverPort + contextPath;
String backUrl = path + "wap/wxPay/backResponse/";
String ip = IPUtils.getRealIP(req);
// 用户openId
UserEntity user = userDao.findOne(RequestUtils.getCurrentUser(req).getId());
if (user.getWeixinOpenId() == null) {
// 可以不需要
throw new BusinessException("请使用微信账号登录");
}
String timeStamp = WeixinSign.create_timestamp();
modelMap.addAttribute("appId", appId);
modelMap.addAttribute("timeStamp", timeStamp);
@SuppressWarnings("unchecked")
Map<String, String> map = WxPayUtil.getWeixinPayMap(appId, appKey, merId, orderId, payAmount, backUrl, ip, user.getWeixinOpenId(),timeStamp);
for (@SuppressWarnings("rawtypes")
Map.Entry entry : map.entrySet()) {
modelMap.addAttribute(entry.getKey().toString(), entry.getValue());
logger.info(entry.getKey().toString(), entry.getValue());
}
if (StringUtils.contains((String) map.get("return_code"), "FAIL")) {
throw new BusinessException((String) map.get("return_msg"));
}
return "/wap/buy/weixinpay_result";
} catch (BusinessException ex) {
modelMap.addAttribute("message", ex.getMessage());
} catch (Exception ex) {
modelMap.addAttribute("message", "系统错误");
}
return "/wap/buy/pay_error";
}
/**
* 支付结果
*
* @param modelMap
* @param req
* @param res
* @return
* @author lvzf 2016年10月8日
*/
@RequestMapping("/qrcodePaySuccess")
public String qrcodePaySuccess(ModelMap modelMap, HttpServletRequest req, HttpServletResponse res, String payNo) {
PayRecordEntity pay = payService.getPayByPayNo(payNo);
if (pay != null && pay.getPayStatus() == PayRecordEntity.PAY_STATUS_SUCCESS) {
return "/wap/buy/pay_result";
}
return "/wap/buy/pay_error";
}
@SuppressWarnings({ "unchecked", "rawtypes" })
@RequestMapping("/backResponse")
public void weixin_notify(HttpServletRequest request, HttpServletResponse response) throws Exception {
// 读取参数
InputStream inputStream;
StringBuffer sb = new StringBuffer();
inputStream = request.getInputStream();
String s;
BufferedReader in = new BufferedReader(new InputStreamReader(inputStream, "UTF-8"));
while ((s = in.readLine()) != null) {
sb.append(s);
}
in.close();
inputStream.close();
// 解析xml成map
Map<String, String> m = new HashMap<String, String>();
m = XMLUtil.doXMLParse(sb.toString());
// 过滤空 设置 TreeMap
SortedMap<Object, Object> packageParams = new TreeMap<Object, Object>();
Iterator it = m.keySet().iterator();
while (it.hasNext()) {
String parameter = (String) it.next();
String parameterValue = m.get(parameter);
String v = "";
if (null != parameterValue) {
v = parameterValue.trim();
}
packageParams.put(parameter, v);
}
logger.info(FastJSONUtils.toJsonString(packageParams));
// 判断签名是否正确
if (WxPayUtil.isTenpaySign("UTF-8", packageParams, appKey)) {
// ------------------------------
// 处理业务开始
// ------------------------------
String resXml = "";
if ("SUCCESS".equals((String) packageParams.get("result_code"))) {
// 这里是支付成功
// ////////执行自己的业务逻辑////////////////
String mch_id = (String) packageParams.get("mch_id");
String openid = (String) packageParams.get("openid");
String is_subscribe = (String) packageParams.get("is_subscribe");
String out_trade_no = (String) packageParams.get("out_trade_no");
String trade_no = request.getParameter("trade_no");
String trade_status = request.getParameter("result_code");
String total_fee = (String) packageParams.get("total_fee");
logger.info("mch_id:" + mch_id);
logger.info("openid:" + openid);
logger.info("is_subscribe:" + is_subscribe);
logger.info("out_trade_no:" + out_trade_no);
logger.info("total_fee:" + total_fee);
// ////////执行自己的业务逻辑////////////////
logger.info("支付成功");
// 通知微信.异步确认成功.必写.不然会一直通知后台.八次之后就认为交易失败了.
resXml = "<xml>" + "<return_code><![CDATA[SUCCESS]]></return_code>" + "<return_msg><![CDATA[OK]]></return_msg>" + "</xml> ";
PayRecordEntity pay = payService.getPayByPayNo(out_trade_no);
if (pay != null && pay.getPayStatus() != PayRecordEntity.PAY_STATUS_SUCCESS) {
pay.setPayStatus(PayRecordEntity.PAY_STATUS_SUCCESS);// 付款
// pay.setThirdPayTime(DateUtil.getStringToDate(notify_time,
// DateUtil.YMDhhmmss));
pay.setThirdPayTime(new Date());
pay.setThirdTradeNo(trade_no);
pay.setThirdTradeStatus(trade_status);
// 生成中奖号码
UserEntity user = userDao.findOne(pay.getUserId());
ygBuyService.createWinNo(user, pay);
}
} else {
logger.info("支付失败,错误信息:" + packageParams.get("err_code"));
resXml = "<xml>" + "<return_code><![CDATA[FAIL]]></return_code>" + "<return_msg><![CDATA[报文为空]]></return_msg>" + "</xml> ";
}
// ------------------------------
// 处理业务完毕
// ------------------------------
BufferedOutputStream out = new BufferedOutputStream(response.getOutputStream());
out.write(resXml.getBytes());
out.flush();
out.close();
} else {
logger.info("通知签名验证失败");
}
}
}
来源:oschina
链接:https://my.oschina.net/u/1052192/blog/760239