iOS如何调用微信支付

微信APP支付

1.到微信开放平台注册并开通开发者资质 <a href="https://open.weixin.qq.com">微信开放平台</a>
2.提交APP应用进行审核,只有审核通过的应用才能正式发布使用。
3.审核通过后APP应用获取支付能力 <a href ="http://kf.qq.com/faq/140225MveaUz150107UVFNjy.html">微信支付商户申请接入</a>
4.<a href ="https://open.weixin.qq.com/cgi-bin/showdocument?action=dir_list&t=resource/res_list&verify=1&id=open1419317780&token=&lang=zh_CN">申请流程指引</a>


CEEBDB64-C03F-4837-B771-6335653A1404.png

调用微信支付Xcode配置

<a href="https://pay.weixin.qq.com/wiki/doc/api/app/app.php?chapter=11_1">官方文档及demol</a>

注册APPID
商户APP工程中引入微信lib库和头文件,调用API前,需要先向微信注册您的APPID,代码如下:
[WXApi registerApp:@"自己的APPID" withDescription:@"WechatPay"];

EA37EBD8-B5E0-4407-8333-C0A70790FDBD.png

1、iOS 9系统策略更新,限制了http协议的访问,此外应用需要在Info.plist中将要使用的URL Schemes列为白名单,才可正常检查其他应用是否安装。
Info.plist **右击->Open As ->Source Code **里添加如下代码

<key>LSApplicationQueriesSchemes</key>
<array>
<string>weixin</string>
</array>
<key>NSAppTransportSecurity</key>
<dict>
<key>NSAllowsArbitraryLoads</key>
<true/>
</dict>

405670BA-AAAE-4BE3-85D8-3212249EA1A9.png

需要导入的静态库文件

SystemConfiguration.framework
libz.tbd
libsqlite3.0.tbd
libc++.tbd
CoreTelephony.framework

首先先调用统一下单接口在微信支付服务后台生成预支付交易单,返回正确的预支付交易回话标识后再在APP里面调起支付。(为了安全,一般调用该接口的需要的参数由后台生成)

统一下单接口 https://api.mch.weixin.qq.com/pay/unifiedorder
后台生成的xml JSON字符串如下格式(也可在前端自己拼接,拼接方式与调起微信支付时生成的参数签名方法一致)

<xml>
<appid>自己的APPID</appid>
<body>商品的标题</body>
<mch_id>商户号</mch_id>
<nonce_str>随机字符串</nonce_str>
<notify_url>后台回调地址异步通知给后台支付结果</notify_url>
<out_trade_no>商户订单号</out_trade_no>
<spbill_create_ip>168.0.0.1</spbill_create_ip>//用户端实际ip
<total_fee>订单总金额,单位为分</total_fee>
<trade_type>APP</trade_type>//固定值
//微信商户平台里面自定义的密钥key和以上参数拼接之后进行MD5获得的签名
<sign>签名</sign>
</xml>

 NSString *paramesXmlString  上面的字符串
//创建URL
   NSURL *unifiedOrderURL = [NSURL URLWithString:@"https://api.mch.weixin.qq.com/pay/unifiedorder"];
    //请求
    NSMutableURLRequest *request = [[NSMutableURLRequest alloc]initWithURL:unifiedOrderURL cachePolicy:NSURLRequestReloadIgnoringLocalCacheData timeoutInterval:5.0];
    [request addValue:@"text/xml" forHTTPHeaderField:@"Content-Type"];
   [request setHTTPMethod:@"POST"];

//paramesXmlString 上面由后台生成的xml JSON字符串;
     NSData *httData = [paramesXmlString dataUsingEncoding:NSUTF8StringEncoding];
 [request setHTTPBody:httData];
 NSURLSessionDataTask *task = [[NSURLSession sharedSession]dataTaskWithRequest:request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
//返回的是xml 进行xml解析
        xmlParser = [[XMLParseManager alloc]initWthXmlData:data andResultBlock:^(NSMutableDictionary *resultDictionary) {

            _prepayid = [resultDictionary objectForKey:@"prepay_id"];
            _noncestr =[resultDictionary objectForKey:@"nonce_str"];
            _mchid =[resultDictionary objectForKey:@"mch_id"];
            _appid =[resultDictionary objectForKey:@"appid"];

            [self payWX];
        }];
        [xmlParser startParse];
    }];
 [task resume];


//微信支付服务后台生成预支付交易单信息
//resultDictionary 
{
    appid = APPID;
    "mch_id" = 商户号;
    "nonce_str" = Ob5KviQMBrJJ9GMK;//随机字符串
    "prepay_id" = wx2016080220898a8b0ag4387943;//支付订单号
    "result_code" = SUCCESS;
    "return_code" = SUCCESS;
    "return_msg" = OK;
    sign = BUHKU849FJLD;
    "trade_type" = APP;
}

得到了微信支付服务后台生成预支付交易单信息,拼接参数并生成签名,最后调起微信支付

    获取当前时间
    time_t now;
    time(&now); 
    NSString *timestamp = [NSString stringWithFormat:@"%ld",now];

   //得到的微信支付后台生成预订单信息
    NSDictionary *dict = @{@"appid":_appid,//APPID
                          @"noncestr":_noncestr,//随机字符串
                          @"package":@"Sign=WXPay",//固定值
                          @"partnerid":_mchid,//商户ID
                          @"prepaid":_prepayid,//支付订单号
                          @"timestamp":timestamp};
    NSMutableString *contentString = [NSMutableString string];
    
    NSArray *keys = [dict allKeys];
    
//按首字母排序
    NSArray *sortedArray = [keys sortedArrayUsingComparator:^NSComparisonResult(id  _Nonnull obj1, id  _Nonnull obj2) {

        return [obj1 compare:obj2 options:NSNumericSearch];

    }];
    
    //拼接字符串
    
    for (NSString *categoryId in sortedArray) {
        
        if (![[dict objectForKey:categoryId]isEqualToString:@""] && ![categoryId isEqualToString:@"sign"] && ![categoryId isEqualToString:@"key"]) {
            
//拼接的时候不要写错%@=%@& 少了&调起微信支付只会有一个确定按钮没有订单信息导致无法支付
            [contentString appendFormat:@"%@=%@&",categoryId,dict[categoryId]];
        }
    }
    
    [contentString appendFormat:@"key=%@",@"微信商户平台里面自定义的密钥key"];
        //加密生成字符串 MD5
        NSString *md5Sign = [WXUtil md5:contentString];
        //调起微信支付
        PayReq* req             = [[PayReq alloc] init];
        req.partnerId           = [dict objectForKey:@"partnerid"];
        req.prepayId            = [dict objectForKey:@"prepayid"];
        req.nonceStr            = [dict objectForKey:@"noncestr"];
        req.timeStamp           = timestamp.intValue;
        req.package             = [dict objectForKey:@"package"];
        req.sign                = md5Sign;
        //最关键的就是这里发送请求到微信,
        [WXApi sendReq:req];
+(NSString *)md5:(NSString *)str{
    const char *cStr = [str UTF8String];
    
    unsigned char digest[CC_MD5_DIGEST_LENGTH];
    
    CC_MD5(cStr,(unsigned int)strlen(cStr),digest);
    
    NSMutableString *output = [NSMutableString stringWithCapacity:CC_MD5_DIGEST_LENGTH * 2];
    
    for (int i = 0; i < CC_MD5_DIGEST_LENGTH; i++) {
        [output appendFormat:@"%02X",digest[i]];
        
    }
return output;
    
}
//  XMLParseManager

//开始xml解析
- (void)startParse{
    
    _xmlParser = [[NSXMLParser alloc]initWithData:_xmlData];
    
    [_xmlParser setDelegate:self];

    [_xmlParser parse];

}
//开始解析的时候,初始化要解析的内容

-(void)parserDidStartDocument:(NSXMLParser *)parser{

    _resultDictionary = [NSMutableDictionary dictionary];
    
    _contentSting = [NSMutableString string];

}
//记录节点内容
-(void)parser:(NSXMLParser *)parser foundCharacters:(NSString *)string{

    [_contentSting setString:string];

}

-(void)parser:(NSXMLParser *)parser didEndElement:(NSString *)elementName namespaceURI:(NSString *)namespaceURI qualifiedName:(NSString *)qName{

    if (![_contentSting isEqualToString:@"\\n"]&& ![elementName isEqualToString:@"root"] ) {
        
        [_resultDictionary setObject:[_contentSting copy] forKey:elementName];
  
    }
}
//解析结果之后,传入一个字典
-(void)parserDidEndDocument:(NSXMLParser *)parser{

    _resultBlock(_resultDictionary);

}

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 159,117评论 4 362
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,328评论 1 293
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 108,839评论 0 243
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 44,007评论 0 206
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,384评论 3 287
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,629评论 1 219
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,880评论 2 313
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,593评论 0 198
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,313评论 1 243
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,575评论 2 246
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,066评论 1 260
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,392评论 2 253
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,052评论 3 236
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,082评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,844评论 0 195
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,662评论 2 274
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,575评论 2 270

推荐阅读更多精彩内容