微信支付V3.x版本实例(上)

微信支付V3.x版本实例(使用SpringMVC+Maven+Jetty)
网页内支付场景---JS API

显示支付安全标题,需将原始链接添加上 "showwxpaytitle=1" 的尾串。通过这种方式,商户页面将出现微信安全支付标识。
例如:htp://weixin.qq.com?showwxpaytitle=1

微信支付实现过程步骤:

微信支付V3.x版本实例(上)_第1张图片


1.获取微信支付配置参数;
微信支付参数需要的有3个:a.微信分配的公众账号ID(appid);b.微信支付分配的商户号(mch_id/PartnerId);c.商户密钥(PartnerKey)

微信支付V3.x版本实例(上)_第2张图片


2.调用统一下单接口,生成预支付订单号:

生成预支付订单号关键代码:

package org.oms.app.service;

import java.util.Map;
import java.util.TreeMap;

import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClientBuilder;
import org.apache.http.util.EntityUtils;
import org.jdom2.JDOMException;
import org.jsoup.Jsoup;
import org.oms.app.util.MD5Util;
import org.oms.app.util.OrderUtil;
import org.oms.app.util.XMLUtil;
/**
 * 生成预支付订单号
 * @author Sunlight
 *
 */
public class WXPrepay {
	private static String unifiedorder = "https://api.mch.weixin.qq.com/pay/unifiedorder";
	private static String orderquery = "https://api.mch.weixin.qq.com/pay/orderquery";
	private String appid;
	private String mch_id;
	private String nonce_str = OrderUtil.CreateNoncestr();
	private String body;
	private String out_trade_no;
	private String total_fee;
	private String spbill_create_ip;
	private String trade_type;
	private String notify_url;
	private String sign;
	private String partnerKey;
	// 预支付订单号
	private String prepay_id;

	/**
	 * 生成预支付订单
	 * 
	 * @return
	 */
	public String submitXmlGetPrepayId() {
		// 创建HttpClientBuilder
		HttpClientBuilder httpClientBuilder = HttpClientBuilder.create();
		// HttpClient
		CloseableHttpClient closeableHttpClient = httpClientBuilder.build();
		HttpPost httpPost = new HttpPost(unifiedorder);
		String xml = getPackage();
		StringEntity entity;
		try {
			entity = new StringEntity(xml, "utf-8");
			httpPost.setEntity(entity);
			HttpResponse httpResponse;
			// post请求
			httpResponse = closeableHttpClient.execute(httpPost);
			HttpEntity httpEntity = httpResponse.getEntity();
			if (httpEntity != null) {
				// 打印响应内容
				String result = EntityUtils.toString(httpEntity, "UTF-8");
				System.out.println(result);
				// 过滤
				result = result.replaceAll("", "");
				String prepay_id = Jsoup.parse(result).select("prepay_id").html();
				this.prepay_id = prepay_id;
				if (prepay_id != null)
					return prepay_id;
			}
			// 释放资源
			closeableHttpClient.close();
		} catch (Exception e) {
			e.printStackTrace();
		}
		return prepay_id;
	}

	/**
	 * 请求订单查询接口
	 */
	@SuppressWarnings("unchecked")
	public Map reqOrderquery() {
		HttpClientBuilder httpClientBuilder = HttpClientBuilder.create();
		CloseableHttpClient closeableHttpClient = httpClientBuilder.build();
		HttpPost httpPost = new HttpPost(orderquery);
		String xml = getPackage();
		StringEntity entity;
		Map map = null;
		try {
			entity = new StringEntity(xml, "utf-8");
			httpPost.setEntity(entity);
			HttpResponse httpResponse;
			// post请求
			httpResponse = closeableHttpClient.execute(httpPost);
			// getEntity()
			HttpEntity httpEntity = httpResponse.getEntity();
			if (httpEntity != null) {
				// 打印响应内容
				String result = EntityUtils.toString(httpEntity, "UTF-8");
				// 过滤
				result = result.replaceAll("", "");
				try {
					map = XMLUtil.doXMLParse(result);
				} catch (JDOMException e) {
					e.printStackTrace();
				}
			}
			// 释放资源
			closeableHttpClient.close();
		} catch (Exception e) {
			e.printStackTrace();
		}
		return map;
	}

	public String getPackage() {
		TreeMap treeMap = new TreeMap();
		treeMap.put("appid", this.appid);
		treeMap.put("mch_id", this.mch_id);
		treeMap.put("nonce_str", this.nonce_str);
		treeMap.put("body", this.body);
		treeMap.put("out_trade_no", this.out_trade_no);
		treeMap.put("total_fee", this.total_fee);
		treeMap.put("spbill_create_ip", this.spbill_create_ip);
		treeMap.put("trade_type", this.trade_type);
		treeMap.put("notify_url", this.notify_url);
		StringBuilder sb = new StringBuilder();
		for (String key : treeMap.keySet()) {
			sb.append(key).append("=").append(treeMap.get(key)).append("&");
		}
		sb.append("key=" + partnerKey);
		sign = MD5Util.MD5Encode(sb.toString(), "utf-8").toUpperCase();
		treeMap.put("sign", sign);
		StringBuilder xml = new StringBuilder();
		xml.append("\n");
		for (Map.Entry entry : treeMap.entrySet()) {
			if ("body".equals(entry.getKey()) || "sign".equals(entry.getKey())) {
				xml.append("<" + entry.getKey() + ">\n");
			} else {
				xml.append("<" + entry.getKey() + ">").append(entry.getValue()).append("\n");
			}
		}
		xml.append("");
		System.out.println(xml.toString());
		return xml.toString();
	}

	public String getAppid() {
		return appid;
	}

	public void setAppid(String appid) {
		this.appid = appid;
	}

	public String getMch_id() {
		return mch_id;
	}

	public void setMch_id(String mch_id) {
		this.mch_id = mch_id;
	}

	public String getBody() {
		return body;
	}

	public void setBody(String body) {
		this.body = body;
	}

	public String getOut_trade_no() {
		return out_trade_no;
	}

	public void setOut_trade_no(String out_trade_no) {
		this.out_trade_no = out_trade_no;
	}

	public String getTotal_fee() {
		return total_fee;
	}

	public void setTotal_fee(String total_fee) {
		this.total_fee = total_fee;
	}

	public String getSpbill_create_ip() {
		return spbill_create_ip;
	}

	public void setSpbill_create_ip(String spbill_create_ip) {
		this.spbill_create_ip = spbill_create_ip;
	}

	public String getTrade_type() {
		return trade_type;
	}

	public void setTrade_type(String trade_type) {
		this.trade_type = trade_type;
	}

	public String getNotify_url() {
		return notify_url;
	}

	public void setNotify_url(String notify_url) {
		this.notify_url = notify_url;
	}

	public String getPartnerKey() {
		return partnerKey;
	}

	public void setPartnerKey(String partnerKey) {
		this.partnerKey = partnerKey;
	}
	
}

微信支付V3.x版本实例(上)_第3张图片


3.生成带支付签名的订单凭据并返回

关键代码:

package org.oms.app.service;

import java.util.Iterator;
import java.util.Map;
import java.util.Random;
import java.util.Set;
import java.util.SortedMap;
import java.util.TreeMap;

import org.oms.app.util.MD5;
import org.oms.app.util.MD5Util;
import org.oms.app.util.OrderUtil;

import net.sf.json.JSONObject;

/**
 * 微信调起支付类
 * 
 * @author Sunlight
 * 
 */
public class WXPay {
	public static String createPackageValue(String appid, String appKey, String prepay_id)  {
		SortedMap nativeObj = new TreeMap();
		nativeObj.put("appId", appid);
		nativeObj.put("timeStamp", OrderUtil.GetTimestamp());
		Random random = new Random();
		String randomStr = MD5.GetMD5String(String.valueOf(random.nextInt(10000)));
		nativeObj.put("nonceStr", MD5Util.MD5Encode(randomStr, "utf-8").toLowerCase());
		nativeObj.put("package", "prepay_id=" + prepay_id);
		nativeObj.put("signType", "MD5");
		nativeObj.put("paySign", createSign(nativeObj, appKey));
		System.out.println(JSONObject.fromObject(nativeObj).toString());
		return JSONObject.fromObject(nativeObj).toString();
	}

	/**
	 * 创建md5摘要,规则是:按参数名称a-z排序,遇到空值的参数不参加签名。
	 */
	public static String createSign(SortedMap packageParams, String AppKey) {
		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=" + AppKey);
		String sign = MD5Util.MD5Encode(sb.toString(), "UTF-8").toUpperCase();
		return sign;
	}
}


微信支付V3.x版本实例(上)_第4张图片


4.调起微信支付(发起微信支付请求)


微信支付V3.x版本实例(上)_第5张图片


5.用户确认金额并输入支付密码


微信支付V3.x版本实例(上)_第6张图片


因上传图片限制,在文章微信支付V3.x版本实例(下) 中继续编写!

代码已上传至开源中国:网页内支付---JS API代码

如果想要体验微信支付快感,请点击此处击地址 

此处需要注意的是:配置支付测试目录并填写支付的3个参数!

你可能感兴趣的:(Wechat)