导入
和支付宝一样拖进去就可以了。报错的话照官方文档拖些库进去。
集成
//设置微信支付
[WXApi registerApp:@"你的AppId" withDescription:@"应用附加信息,我写的是bundelID+一些字符"];
如果你用了友盟的分享的话最好把分享的方法放在前面。
[UMSocialWechatHandler setWXAppId:@"" appSecret:@"" url:@""];
生成订单
有一点要注意的是微信的支付单位为分,要支付1块钱就要传100过去。 同样微信也是应该在服务器进行签名,如果要本地签名就先创建一个字典,设置下面的这些参数。
| 参数名 | 值 | |——–|——–| | appid | 开放平台appid | | mch_id | 商户号 | | nonce_str | 随机串 | | trade_type | 支付类型,固定为APP | | body | 订单描述,展示给用户 | | out_trade_no | 商户订单号 | | total_fee | 订单金额,单位为分 | | spbill_create_ip | 发器支付的机器ip | | notify_url | 支付结果异步通知 | |sign|对上面的参数签名得到的| 把这个字典签名去掉微信的统一下单接口
签名的代码
- (NSString *)genSign:(NSDictionary *)signParams
{
// 排序, 因为微信规定 ---> 参数名ASCII码从小到大排序
NSArray *keys = [signParams allKeys];
NSArray *sortedKeys = [keys sortedArrayUsingComparator:^NSComparisonResult(id obj1, id obj2) {
return [obj1 compare:obj2 options:NSNumericSearch];
}];
//生成 ---> 微信规定的签名格式
NSMutableString *sign = [NSMutableString string];
for (NSString *key in sortedKeys) {
[sign appendString:key];
[sign appendString:@"="];
[sign appendString:[signParams objectForKey:key]];
[sign appendString:@"&"];
}
NSString *signString = [[sign copy] substringWithRange:NSMakeRange(0, sign.length - 1)];
// 拼接API密钥
NSString *result = [NSString stringWithFormat:@"%@&key=%@", signString, WXAPIKey];
// 打印检查
NSLog(@"result = %@", result);
// md5加密
NSString *signMD5 = [CommonUtil md5:result];
// 微信规定签名英文大写
signMD5 = signMD5.uppercaseString;
// 打印检查
NSLog(@"signMD5 = %@", signMD5);
return signMD5;
}
第二次签名
微信同意下单接口会返回一个字典,但是我们只需要里面的prepayid这个参数,重新创建一个字典包含下面的参数
参数名 | 值 |
---|---|
appid | 开放平台appid |
partnerid | 商户号 |
noncestr | 随机串 |
package | Sign=WXPay不变 |
timestamp | 时间戳 |
prepayid | 统一下单接口返回的 |
sign | 对上面的参数签名得到的 |
调用微信的支付接口
如果你们的后台直接签完名给你,你可以直接从这里开始看,用后台传给你的字典直接调用微信的支付放久就OK了
[WXApi sendReq:request];//request是拥有上面这些值得字典
回调
回调先要在AppDelegate的这个方法里面加入
- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication:(NSString *)sourceApplication annotation:(id)annotation{
//先判断是微信支付返回的
if([url.absoluteString rangeOfString:@"你的WXAppId://pay"].length){
//调用代理的方法执行支付完成回调
return [WXApi handleOpenURL:url delegate:实现了代理方法的对象];
}
}
代理要实现这个方法
-(void)onResp:(BaseResp*)resp{
if ([resp isKindOfClass:[PayResp class]]){
PayResp*response=(PayResp*)resp;
switch(response.errCode){
case WXSuccess:
NSLog(@"支付成功");
break;
default:
NSLog(@"支付失败");
break;
}
}
}
优化
支付宝和微信属于一个支付管理单例来管理 我对微信的方法进行了封装,变成了下面这个样子
//通过微信的订单类来发起支付
-(void)weixinPayWithPayReq:(PayReq *)payReq andSuc:(weixinSuc)suc andErr:(weixinErr)err{
self.weixinSuc=suc;
self.weixinErr=err;
[WXApi sendReq:payReq];
}
//通过后台返回的数据来发起支付
-(void)weixinPayWithdatePay:(NSDictionary *)datePay andSuc:(weixinSuc)suc andErr:(weixinErr)err{
PayReq *request = [[PayReq alloc] init];
request.partnerId = datePay[@"partnerid"];//商户号
request.prepayId= datePay[@"prepayid"];//预支付交易会话ID
request.package = @"Sign=WXPay";//扩展字段
request.nonceStr= datePay[@"noncestr"];//随机字符串
request.timeStamp= [datePay[@"timestamp"] intValue];//时间戳
request.sign= datePay[@"sign"];//签名
[self weixinPayWithPayReq:request andSuc:suc andErr:err];
}
这样在外边只需要把支付完成或失败后的代码写在block里面就可以了