First of all, Tucao, WeChat's documents and WeChat's demo are really miserable. It took a long time to get it done. If there are still problems, please check carefully whether the parameters are correct or not.
1. The first step is to obtain the application's MD5 signature information.
If you do not configure keytool environments, you can also use them directly. Information provided by Wechat for obtaining package signatures
2. The application process will not be mentioned, please note that the application package name and signature information must be filled in correctly. At first, I made a mistake in the signature information, which was tortuous for a long time.
3. After the application is completed, access is now started.
dependencies {
compile 'com.tencent.mm.opensdk:wechat-sdk-android-without-mta:+'
}
- Register APPID
final IWXAPI msgApi = WXAPIFactory.createWXAPI(context, null);
// Register the app to Wechat
msgApi.registerApp("wxd930ea5d5a258f4f");
- Uniform order The purpose is to get the prepay_id returned to us by wechat
- URL address: https://api.mch.weixin.qq.com/pay/unifiedorder
- It is important to note that the URL needs to post the request.
- stay autograph When the parameter names are sorted from small to large according to ASCII codes
public String getOderXml() {
Map<String, String> oderMap = new HashMap<>();
oderMap.put("appid", appid); //
oderMap.put("mch_id", mch_id);//
oderMap.put("device_info", device_info);//-
oderMap.put("nonce_str", nonce_str);//
oderMap.put("trade_type", trade_type);
oderMap.put("body", body);
oderMap.put("detail", detail);
oderMap.put("out_trade_no", out_trade_no);
oderMap.put("total_fee", total_fee);
oderMap.put("spbill_create_ip", spbill_create_ip);
oderMap.put("time_start", time_start);
oderMap.put("notify_url", notify_url);
//Splice strings with key values, then decrypt sign md5, and then capitalize it
//The parameters of non-null parameter values in set M are sorted from small to large according to parameter name ASCII code
StringBuilder sign = new StringBuilder();
TreeSet<String> set = new TreeSet<>(new Comparator<String>() {
@Override
public int compare(String lhs, String rhs) {
int i = rhs.compareTo(lhs);
if (i > 0) {
return -1;
} else if (i < 0) {
return 1;
} else {
return i;
}
}
});
set.addAll(oderMap.keySet());
for (String str : set) {
sign.append(str).append("=").append(oderMap.get(str)).append("&");
}
sign.append("key").append("=").append(WechatUtil.KEY);
oderMap.put("sign", StringUtil.md5(sign.toString()).toUpperCase());
//Strings spliced into xml format
StringBuilder stringBuilder = new StringBuilder();
stringBuilder.append("<xml>");
set.clear();
set.addAll(oderMap.keySet());
for (String s : set) {
stringBuilder.append("<").append(s).append(">");
stringBuilder.append(oderMap.get(s));
stringBuilder.append("</").append(s).append(">");
}
stringBuilder.append("</xml>");
return stringBuilder.toString();
}
//Processing xml data returned by wechat
public OderResult xmlToResult(String xml) {
XmlPullParser pullParser = Xml.newPullParser();
InputStream ins = new ByteArrayInputStream(xml.getBytes());
OderResult result = new OderResult();
try {
pullParser.setInput(ins, "utf-8");
int eventType = pullParser.getEventType();
while (XmlPullParser.END_DOCUMENT != eventType) {
switch (eventType) {
case XmlPullParser.START_TAG:
if ("return_code".equals(pullParser.getName())) {
result.setReturn_code(pullParser.nextText());
}
if ("return_msg".equals(pullParser.getName())) {
result.setReturn_msg(pullParser.nextText());
}
if ("appid".equals(pullParser.getName())) {
result.setAppid(pullParser.nextText());
}
if ("mch_id".equals(pullParser.getName())) {
result.setMch_id(pullParser.nextText());
}
if ("device_info".equals(pullParser.getName())) {
result.setDevice_info(pullParser.nextText());
}
if ("nonce_str".equals(pullParser.getName())) {
result.setNonce_str(pullParser.nextText());
}
if ("sign".equals(pullParser.getName())) {
result.setSign(pullParser.nextText());
}
if ("prepay_id".equals(pullParser.getName())) {
result.setPrepay_id(pullParser.nextText());
}
if ("trade_type".equals(pullParser.getName())) {
result.setTrade_type(pullParser.nextText());
}
if ("result_code".equals(pullParser.getName())) {
result.setResult_code(pullParser.nextText());
}
break;
case XmlPullParser.END_TAG:
break;
default:
break;
}
eventType = pullParser.next();
}
} catch (XmlPullParserException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
return result;
}
//Random string, no longer than 32 bits
public String getRandom() {
SimpleDateFormat format = new SimpleDateFormat("yyMMddHHmmss", Locale.getDefault());
Date date = new Date();
String key = format.format(date);
Random r = new Random();
key = key + r.nextLong();
key = StringUtil.md5(key);
return key;
}
- Payment mobilization The signature method is the same as the above processing.
IWXAPI api;
PayReq request = new PayReq();
request.appId = "wxd930ea5d5a258f4f";
request.partnerId = "1900000109";
request.prepayId= "1101000000140415649af9fc314aa427",;
request.packageValue = "Sign=WXPay";
request.nonceStr= "1101000000140429eb40476f8896f4c9";
request.timeStamp= "1398746574";
request.sign= "7FFECB600D7157C5AA49810D2D8F28BC2811827B";
api.sendReq(request);
- Payment result callback to implement a. wxapi. WXPayEntry Activity (inconsistent package or class names can cause callbacks). If you don't need to display this, just finish it.
<activity
android:name=".wxapi.WXPayEntryActivity"
android:exported="true" />
public class WXPayEntryActivity extends Activity implements IWXAPIEventHandler {
private IWXAPI api;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
api = WXAPIFactory.createWXAPI(this, WechatUtil.APPID, false);
api.handleIntent(getIntent(), this);
}
@Override
public void onReq(BaseReq baseReq) {
}
@Override
protected void onNewIntent(Intent intent) {
super.onNewIntent(intent);
setIntent(intent);
api.handleIntent(intent, this);
}
@Override
public void onResp(BaseResp baseResp) {
if (baseResp.getType() == ConstantsAPI.COMMAND_PAY_BY_WX) {
if (baseResp.errCode == BaseResp.ErrCode.ERR_COMM) {
showToast("Wechat Payment Failed");
} else if (baseResp.errCode == BaseResp.ErrCode.ERR_USER_CANCEL) {
showToast("User Cancel");
} else if (baseResp.errCode == BaseResp.ErrCode.ERR_OK) {
showToast("Wechat Payment Successful");
}
}
}
}
- If the return is a failure, please check carefully whether the parameters of invoking payment are correct, the parameters of signing signature are correct, and if not, please check again. There is too little error information about Wechat payment, only success and failure. If the unified order is successful, then you must start the invocation. Payment of parameter errors, please check carefully, important things repeated three times.
- If there is a problem when placing a unified order, please confirm whether the order number returned to you from the background is unique, whether the parameters are correct, when signing, whether it is MD5 signature filled in by the Wechat platform, whether the way to initiate the request is post, whether it is transmitting XML data, and if it is initiated by using Retrofit. The request may be as follows:
new Retrofit.Builder()
.baseUrl("https://api.mch.weixin.qq.com/pay/")
.addConverterFactory(StringConverterFactory.create())
.build()
.create(API.class)
.oder(RequestBody.create(MediaType.parse("text/plain"), oder)).enqueue(new Callback<String>() {
@Override
public void onResponse(Call<String> call, Response<String> response) {
if (response.body() != null) {
OderResult result = xmlToResult(response.body());
if (result.getReturn_code().equals("SUCCESS")) {
if (result.getResult_code().equals("SUCCESS")) {
}
} else {
}
}
}
@Override
public void onFailure(Call<String> call, Throwable t) {
}
});
private interface API {
@POST("unifiedorder")
Call<String> oder(@Body RequestBody oder);
}