iOS支付
iOS支付分為兩類火鼻,第三方支付和應用內(nèi)支付(內(nèi)購)竹握。
第三方支付包括:支付寶支付熔掺、微信支付铆帽、銀聯(lián)支付致扯、百度錢包蛇更、京東支付等等错妖。
應用內(nèi)支付(In-App Purchase):在應用程序內(nèi)購買虛擬商品揭保。如果你在App Store上銷售的應用程序知押,將收到支付金額的70%叹螟。
第三方支付
彈出方式
網(wǎng)頁
有些第三方支付沒有安裝客戶端鹃骂,可以直接彈出網(wǎng)頁進行支付。(比如支付寶)
調用APP
手機中安裝了客戶端可以跳轉到APP中進行支付罢绽。微信支付只能調用App進行支付畏线。
支付寶支付
相關資料
- 支付寶開放平臺(SDK&開發(fā)文檔):https://open.alipay.com/platform/home.htm
- 移動支付集成:https://doc.open.alipay.com/doc2/detail?treeId=59&articleId=103563&docType=1
- 商戶服務平臺(與支付寶簽約需要填寫的公司資料):https://b.alipay.com/newIndex.htm
支付流程
-
在商戶服務平臺先與支付寶簽約,獲得商戶ID(partner)和賬號ID(seller)良价,需要提供公司資質或者營業(yè)執(zhí)照寝殴,個人無法申請。
文檔地址:https://doc.open.alipay.com/doc2/detail?treeId=58&articleId=103542&docType=1
-
生成并下載相應的公鑰私鑰文件(加密簽名用)
文檔地址:https://doc.open.alipay.com/doc2/detail.htm?spm=0.0.0.0.POMYKl&treeId=58&articleId=103543&docType=1
下載支付寶SDK:https://doc.open.alipay.com/doc2/detail?treeId=54&articleId=103419&docType=1
生成訂單信息
調用支付寶客戶端明垢,由支付寶客戶端跟支付寶安全服務器打交道
支付完畢后返回支付結果給商戶客戶端和服務器
SDK里有集成支付寶功能的一個Demo蚣常,集成支付功能的具體操作方式,可以參考Demo痊银。
代碼集成流程
參考文檔地址:https://doc.open.alipay.com/doc2/detail.htm?spm=0.0.0.0.efmKDS&treeId=59&articleId=103676&docType=1
-
下載官方SDK
下載地址:https://doc.open.alipay.com/doc2/detail?treeId=54&articleId=103419&docType=1
本Demo使用的SDK是從官方Demo整理出來的抵蚊,整理的SDK版本:201501022。
下載地址:http://7xooko.com1.z0.glb.clouddn.com/AlipaySDK.zip
目錄結構如下:
├── AlipaySDK.bundle ├── AlipaySDK.framework ├── Order.h ├── Order.m ├── Util ├── libcrypto.a ├── libssl.a └── openssl
其中:
-
AlipaySDK.bundle
和AlipaySDK.framework
是支付寶SDK -
Order
類:定義訂單信息 -
Util溯革、libcrypto.a贞绳、libssl.a、openssl
:數(shù)據(jù)簽名致稀,對訂單信息進行加密
-
-
添加依賴庫
其中冈闭,需要注意的是:
如果是Xcode 7.0之后的版本,需要添加libc++.tbd抖单、libz.tbd萎攒;
如果是Xcode 7.0之前的版本,需要添加libc++.dylib矛绘、libz.dylib躺酒。
-
創(chuàng)建
prefix header file
PCH文件,添加#import <Foundation/Foundation.h>
在
Build Settings
中的prefix header
設置pch文件路徑 在
Build Settings
中Header Search Paths
添加頭文件引用路徑蔑歌,[文件路徑]/AlipaySDK/
-
在需要調用AlipaySDK的文件中羹应,增加頭文件引用。
#import <AlipaySDK/AlipaySDK.h> #import "Order.h" #import "DataSigner.h"
-
生成訂單信息及簽名
//將商品信息賦予AlixPayOrder的成員變量 Order *order = [[Order alloc] init]; order.partner = PartnerID; // 商戶ID order.seller = SellerID; // 賬號ID order.tradeNO = @"20150923"; //訂單ID(由商家自行制定) order.productName = @"iPhone6s"; //商品標題 order.productDescription = @"新年打折"; //商品描述 order.amount = @"0.01"; //商品價格(單位:元) order.notifyURL = @"http://www.chaosky.me"; //回調URL次屠,支付成功或者失敗回調通知自己的服務器進行訂單狀態(tài)變更 order.service = @"mobile.securitypay.pay"; order.paymentType = @"1"; order.inputCharset = @"utf-8"; order.itBPay = @"30m"; order.showUrl = @"m.alipay.com"; // 應用注冊scheme,在AlixPayDemo-Info.plist定義URL types NSString *appScheme = @"AliPayDemo"; //將商品信息拼接成字符串 NSString *orderSpec = [order description]; NSLog(@"orderSpec = %@",orderSpec); //獲取私鑰并將商戶信息簽名,外部商戶可以根據(jù)情況存放私鑰和簽名,只需要遵循RSA簽名規(guī)范,并將簽名字符串base64編碼和UrlEncode id<DataSigner> signer = CreateRSADataSigner(PartnerPrivKey); NSString *signedString = [signer signString:orderSpec]; //將簽名成功字符串格式化為訂單字符串,請嚴格按照該格式 NSString *orderString = nil; if (signedString != nil) { orderString = [NSString stringWithFormat:@"%@&sign=\"%@\"&sign_type=\"%@\"", orderSpec, signedString, @"RSA"]; [[AlipaySDK defaultService] payOrder:orderString fromScheme:appScheme callback:^(NSDictionary *resultDic) { NSLog(@"reslut = %@",resultDic); }]; }
-
Xcode設置URL scheme
iPhone SDK可以把你的App和一個自定義的URL Scheme綁定园匹。該URL Scheme可用來從瀏覽器或別的App啟動你的App。
配置方法:打開info.plist文件劫灶,找到或者添加如圖所示的鍵值對:
URL Scheme值為代碼中對應的值裸违,必須一致。
-
配置支付寶客戶端返回url處理方法
AppDelegate.m文件中本昏,增加引用代碼:
#import <AlipaySDK/AlipaySDK.h>
在@implementation AppDelegate中增加如下代碼:
- (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication:(NSString *)sourceApplication annotation:(id)annotation { //如果極簡開發(fā)包不可用供汛,會跳轉支付寶錢包進行支付,需要將支付寶錢包的支付結果回傳給開發(fā)包 if ([url.host isEqualToString:@"safepay"]) { [[AlipaySDK defaultService] processOrderWithPaymentResult:url standbyCallback:^(NSDictionary *resultDic) { //【由于在跳轉支付寶客戶端支付的過程中,商戶app在后臺很可能被系統(tǒng)kill了怔昨,所以pay接口的callback就會失效雀久,請商戶對standbyCallback返回的回調結果進行處理,就是在這個方法里面處理跟callback一樣的邏輯】 NSLog(@"result = %@",resultDic); }]; } if ([url.host isEqualToString:@"platformapi"]){//支付寶錢包快登授權返回authCode [[AlipaySDK defaultService] processAuthResult:url standbyCallback:^(NSDictionary *resultDic) { //【由于在跳轉支付寶客戶端支付的過程中,商戶app在后臺很可能被系統(tǒng)kill了趁舀,所以pay接口的callback就會失效赖捌,請商戶對standbyCallback返回的回調結果進行處理,就是在這個方法里面處理跟callback一樣的邏輯】 NSLog(@"result = %@",resultDic); }]; } return YES; }
微信支付
需要提供公司資質或者營業(yè)執(zhí)照,個人無法申請矮烹。
相關文檔
- 微信開放平臺:https://open.weixin.qq.com
- 微信支付商戶平臺:https://pay.weixin.qq.com/index.php
- 微信公眾平臺:https://mp.weixin.qq.com
支付流程
-
向微信注冊你的應用程序id
開發(fā)者應用登記頁面進行登記越庇,登記并選擇移動應用進行設置后,將獲得AppID奉狈,可立即用于開發(fā)卤唉。但應用登記完成后還需要提交審核,只有審核通過的應用才能正式發(fā)布使用仁期。
-
微信APP支付接入商戶服務中心
-
下載微信SDK文件搬味,如果在項目中應使用SDK的最新版。
本Demo使用的SDK是從官方Demo整理出來的蟀拷,整理的SDK版本:1.6.1碰纬。
下載地址:http://7xooko.com1.z0.glb.clouddn.com/AlipaySDK.zip
目錄結構如下:
├── SDKExport │ ├── WXApi.h │ ├── WXApiObject.h │ ├── libWeChatSDK.a │ └── read_me.txt └── lib ├── ApiXml.h ├── ApiXml.mm ├── WXUtil.h ├── WXUtil.mm ├── payRequsestHandler.h └── payRequsestHandler.mm
其中:
SDKExport
文件夾:SDK文件lib
文件夾:工具類 -
添加依賴庫
SystemConfiguration.framework libz.dylib libsqlite3.dylib libc++.dylib CoreTelephony.framework CoreGraphics.framework
-
Xcode設置URL scheme
在Xcode中,選擇你的工程設置項问芬,選中“TARGETS”一欄悦析,在“info”標簽欄的“URL type“添加“URL scheme”為你所注冊的應用程序id(如下圖所示)。
-
在你需要使用微信終端API的文件中import WXApi.h 頭文件此衅,并增加 WXApiDelegate 協(xié)議强戴。
// 微信所有的API接口 #import "WXApi.h" // APP端簽名相關頭文件 #import "payRequsestHandler.h" @interface AppDelegate ()<WXApiDelegate> @end
-
要使你的程序啟動后微信終端能響應你的程序,必須在代碼中向微信終端注冊你的id挡鞍。(如下圖所示骑歹,在 AppDelegate 的 didFinishLaunchingWithOptions 函數(shù)中向微信注冊id)。
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions { // Override point for customization after application launch. //向微信注冊 [WXApi registerApp:APP_ID withDescription:@"demo 2.0"]; return YES; }
重寫AppDelegate的handleOpenURL和openURL方法:
- (BOOL)application:(UIApplication *)application handleOpenURL:(NSURL *)url { return [WXApi handleOpenURL:url delegate:self]; } - (BOOL)application:(UIApplication *)application openURL:(NSURL *)url sourceApplication:(NSString *)sourceApplication annotation:(id)annotation { return [WXApi handleOpenURL:url delegate:self]; }
-
現(xiàn)在墨微,你的程序要實現(xiàn)和微信終端交互的具體請求與回應道媚,因此需要實現(xiàn)WXApiDelegate協(xié)議的兩個方法:
-(void) onReq:(BaseReq*)req { if([req isKindOfClass:[GetMessageFromWXReq class]]) { // 微信請求App提供內(nèi)容, 需要app提供內(nèi)容后使用sendRsp返回 NSString *strTitle = [NSString stringWithFormat:@"微信請求App提供內(nèi)容"]; NSString *strMsg = @"微信請求App提供內(nèi)容翘县,App要調用sendResp:GetMessageFromWXResp返回給微信"; UIAlertView *alert = [[UIAlertView alloc] initWithTitle:strTitle message:strMsg delegate:self cancelButtonTitle:@"OK" otherButtonTitles:nil, nil]; alert.tag = 1000; [alert show]; } else if([req isKindOfClass:[ShowMessageFromWXReq class]]) { ShowMessageFromWXReq* temp = (ShowMessageFromWXReq*)req; WXMediaMessage *msg = temp.message; //顯示微信傳過來的內(nèi)容 WXAppExtendObject *obj = msg.mediaObject; NSString *strTitle = [NSString stringWithFormat:@"微信請求App顯示內(nèi)容"]; NSString *strMsg = [NSString stringWithFormat:@"標題:%@ \n內(nèi)容:%@ \n附帶信息:%@ \n縮略圖:%lu bytes\n\n", msg.title, msg.description, obj.extInfo, msg.thumbData.length]; UIAlertView *alert = [[UIAlertView alloc] initWithTitle:strTitle message:strMsg delegate:self cancelButtonTitle:@"OK" otherButtonTitles:nil, nil]; [alert show]; } else if([req isKindOfClass:[LaunchFromWXReq class]]) { //從微信啟動App NSString *strTitle = [NSString stringWithFormat:@"從微信啟動"]; NSString *strMsg = @"這是從微信啟動的消息"; UIAlertView *alert = [[UIAlertView alloc] initWithTitle:strTitle message:strMsg delegate:self cancelButtonTitle:@"OK" otherButtonTitles:nil, nil]; [alert show]; } }
onReq是微信終端向第三方程序發(fā)起請求最域,要求第三方程序響應。第三方程序響應完后必須調用sendRsp返回锈麸。在調用sendRsp返回時镀脂,會切回到微信終端程序界面。
-(void) onResp:(BaseResp*)resp { NSString *strMsg = [NSString stringWithFormat:@"errcode:%d", resp.errCode]; NSString *strTitle; if([resp isKindOfClass:[SendMessageToWXResp class]]) { strTitle = [NSString stringWithFormat:@"發(fā)送媒體消息結果"]; } if([resp isKindOfClass:[PayResp class]]){ //支付返回結果忘伞,實際支付結果需要去微信服務器端查詢 strTitle = [NSString stringWithFormat:@"支付結果"]; switch (resp.errCode) { case WXSuccess: strMsg = @"支付結果:成功薄翅!"; NSLog(@"支付成功-PaySuccess沙兰,retcode = %d", resp.errCode); break; default: strMsg = [NSString stringWithFormat:@"支付結果:失敗翘魄!retcode = %d, retstr = %@", resp.errCode,resp.errStr]; NSLog(@"錯誤鼎天,retcode = %d, retstr = %@", resp.errCode,resp.errStr); break; } } UIAlertView *alert = [[UIAlertView alloc] initWithTitle:strTitle message:strMsg delegate:self cancelButtonTitle:@"OK" otherButtonTitles:nil, nil]; [alert show]; }
如果第三方程序向微信發(fā)送了sendReq的請求,那么onResp會被回調熟丸。sendReq請求調用后,會切到微信終端程序界面