Apple Pay的使用

轉載自:Apple Pay的使用

Apple Pay的使用

關于Apple Pay 具體繼承步驟也可參考: 網址
配置支付環境創建支付請求授權支付支付處理Part 1 關于Apple Pay
Apple Pay是一種移動支付技術,它能夠讓用戶以一種便捷安全的方式為現實世界中購買的商品和服務付款。

在Xcode和蘋果開發者會員中心中配置Apple Pay

使用Apple Pay的APP需要一項特殊的權限,該權限可以在開發者會員中心和Xcode中開啟。你同樣需要注冊一個商業標示,并設置密鑰;在給服務器發送支付信息時,這些密匙可以確保數據的安全傳輸。
相關章節:配置支付環境(Configuring Your Environment,后面會提到)

用戶授權支付請求

支付請求就是描述當前進行的購買操作,包括支付金額。你把支付請求發送給一個授權支付的視圖控制器;該試圖控制器呈現相關請求內容,并提示用戶需要輸入的信息,例如配送地址或者賬單地址。接著,當用戶與視圖控制器交互,并提供新的支付信息時,APP會調用支付請求的委托,繼續執行支付流程。
相關章節:創建支付請求(Creating a Payment Request),授權支付(Authorizing a Payment)(后面會提到)

服務器處理支付請求

Apple Pay會對支付信息進行加密處理,以防止未獲授權的第三方獲取用戶的支付信息。你可以在自己的服務器上完成整個支付流程,也可以在自己的服務器上使用第三方支付平臺來解碼支付信息,并完成支付處理。
關于支持Apple Pay的支付平臺信息,請參考developer.apple.com/apple-pay/
相關章節:處理支付請求(Processing a Payment

Part 2 配置支付環境

一個商用ID標識可以幫助Apple Pay識別你,讓你能夠接受付款。在支付信息加密的過程中,把公匙和證書與ID標示關聯起來進行加密是必不可少的一步。在APP使用Apple Pay之前,你首先得注冊一個商用ID,并配置它的相關證書。

注冊商用ID標示
  • 1.在開發者會員中心,選擇“Certificates,Identifiers&Profiles”
  • 2.在Identifiers下,選擇Merchant IDs
  • 3.在右上角點擊"+"按鈕
  • 4.在Description欄、ID欄輸入相應信息,點擊"Continue"
  • 5.瀏覽下配置參數,點擊"Register"
  • 6.點擊"Done"
為你的ID標示配置一個證書
  • 1.在開發者會員中心,選擇"Certificates,Identifiers&Profiles"
  • 2.在Identifiers下,選擇Merchant IDs
  • 3.選擇列表中的ID標示,點擊Edit
  • 4.點擊"Create Certificate",按照指示獲取或生成簽名證書請求(CSR),點擊"Continue"
  • 5.點擊"Choose File",選擇你的CSR,點擊"Generate"
  • 6.點擊"Download"下載證書,點擊"Done"

如果KeyChain Access中顯示了警示信息,表示未知授權簽發證書或者無效證書發行人,那么要確保你已經在鑰匙鏈中安裝了WWDR中級證書-G2和Apple Root CA-G2。你可以在這個地方下載這些東西:apple.com/certificateauthority.

為了在Xcode中啟用Apple Pay,打開APP工程文件的Capabilities面板。在Apple Pay這行將開關按鈕設置為"ON",接著選擇APP需要使用的ID標示。

注意:在APP排錯時,偶爾手動啟用Apple Pay很管用。請按照以下步驟手動啟用Apple Pay:
  • 1.在會員中心,選擇Certificates,Identifiers& Profiles
  • 2.在Identifiers下,選擇App IDs
  • 3.選擇列表中的app ID,點擊"Edit"
  • 4.選擇 Apple Pay ,點擊"Edit"
  • 5.選擇你需要使用的ID標示,點擊"Continue"
  • 6.瀏覽配置參數,點擊"Assign"
  • 7.點擊"Done"

Part 3 創建支付請求

創建支付請求

支付請求是PKPaymentRequest類的實例,它的組成部分包括一個用來表示將要購買的項目的摘要,一個可用的配送方式列表,一個表示用戶需要提供的配送信息的描述,以及一些商家和支付平臺的信息。
判定用戶是否能夠支付

在創建支付請求之前,要首先通過調用PKPaymentAuthorizationViewController 類里的canMakePaymentsUsingNetworks:方法來判斷用戶是否能夠使用你提供的支付網絡進行支付。如果要判斷用戶的硬件是否支持Apple Pay或者是否因為家長控制而不能支付,請使用canMakePayments 方法。

如果用戶不能進行支付,那就不要顯示支付按鈕,相應的應該退回到其它支付方式。

支付請求包含貨幣和地區信息

所有的匯總金額應該使用同一種貨幣,貨幣的信息可使用PKPaymentRequest類的currencyCode屬性進行指定。像"USD"這樣,使用3個字符格式的ISO貨幣編碼。
一個支付請求里的國家代碼表示了這次購買發生的國家或者將要在這個國家處理這次支付。像"US"這樣,使用2個字符格式的ISO國家編碼。
在支付請求里指定的商用ID必須匹配應用中指定的商用ID列表之一。

request.currencyCode = @"USD";
request.countryCode = @"US";
request.merchantIdentifier = @"merchant.com.example";
支付請求包含一個支付摘要項目的列表

支付摘要項目,屬于PKPaymentSummaryItem 類,描述了支付請求的不同部分。在一個支付請求里不要使用太多的摘要項目---典型的項目像比如小計金額、折扣信息、配送信息、含稅信息以及總計金額等。如果你想要提供更詳細的支付項目列表,可以在你應用的其它地方提供。
每一個摘要項目會有一個標簽和數額,就像在代碼列表3-1中顯示的那樣。標簽文本是一個用戶可閱讀的摘要項目描述信息,數額是相對應的支付數額。在一個支付請求中所有的數額都要使用在這個請求中指定的貨幣。對于折扣或優惠券,則需要把數額設成負數。

Listing 3-1創建支付項目
// 12.75 subtotal
NSDecimalNumber *subtotalAmount = [NSDecimalNumber decimalNumberWithMantissa:1275 exponent:-2 isNegative:NO];
self.subtotal = [PKPaymentSummaryItem summaryItemWithLabel:@"Subtotal" amount:subtotalAmount];
  
// 2.00 discount
NSDecimalNumber *discountAmount = [NSDecimalNumber decimalNumberWithMantissa:200 exponent:-2 isNegative:YES];
self.discount = [PKPaymentSummaryItem summaryItemWithLabel:@"Discount" amount:discountAmount];
注意

這里使用NSDecimalNumber類來存儲摘要項目的數額,它是一個以10為底數的數值。可以使用指定尾數和指數的方式(像代碼中那樣)來創建這個類的實例,也可以通過指定字符串和locale來實例化,字符串指定了相應的數值。這里總是使用以10為底數的數值來做財務計算--例如當需要計算5%折扣掉的金額時。
盡管有時使用其它的計數方法更方便,但是像float或者Double這樣的IEEE浮點數類型是不適合作財務計算的,這些數據類型使用的是以2為底數的數值表示方法,這就表示有一些十進制數值不能準確得被表示--例如0.42必須以0.41999這樣的循環小數來近似表示,而這種近似表示常常會造成財務計算的錯誤結果。
在這個摘要項目列表中的最后一個是總計金額。這個金額是通過把所有其它金額相加而得到。總計的顯示方法和其它的摘要項目不同:應該使用你公司的名稱做為其標簽,使用所有其它項目的金額總和做為金額。使用paymentSummaryItems屬性將這些摘要項目加入支付請求。

// 10.75 grand total
NSDecimalNumber *totalAmount = [NSDecimalNumber zero];
totalAmount = [totalAmount decimalNumberByAdding:subtotalAmount];
totalAmount = [totalAmount decimalNumberByAdding:discountAmount];
self.total = [PKPaymentSummaryItem summaryItemWithLabel:@"My Company Name" amount:totalAmount];
self.summaryItems = @[self.subtotal, self.discount, self.total];
request.paymentSummaryItems = self.summaryItems;
配送方式是一種特殊的摘要項目

對于每一種可用的配送方式創建一個PKShippingMethod的實例。就像其它支付摘要項目一樣,配送方式包含用戶易于辨別的標簽,比如"標準配送"或者"第二天配送",還有一個金額來表示配送費用。與其它摘要項目不同的是,配送方式還有一個detail屬性--像"7月29日到達"或者"24小時之內配送"等--可以用來解釋各個配送方式之間的區別。
使用identifier屬性來在代理方法中區分不同的配送方式,這個屬性只會在你的應用內使用--框架看不到這個屬性,并且它也不會出現在UI中。在創建配送方式時為其分配一個獨一無二的標識符。為了方便調試,可使用文本縮寫,比如"discount", "standard", 或者 "next-day".
有一些配送方式在某些地區可能不適用,或者有不同的價格,你可以在用戶選擇配送地址或配送方式的代理方法時更新這些信息,就像Your Delegate Updates Shipping Methods and Costs描述的一樣。

指定你支持的支付方式

通過在supportedNetworks屬性中填入字符串常量數組來指定你支持的支付網絡。通過指定merchantCapabilities屬性來指定你支持的支付處理標準,3DS支付方式是必須支持的,EMV方式是可選的。
商家支持的支付處理標準使用標識位來進行組合,像下面這樣:

request.supportedNetworks = @[PKPaymentNetworkAmex, PKPaymentNetworkMasterCard, PKPaymentNetworkVisa];
// Supports 3DS only
request.merchantCapabilities = PKMerchantCapability3DS;
// Supports both 3DS and EMV
request.merchantCapabilities = PKMerchantCapability3DS | PKMerchantCapabilityEMV;
指示所需配送信息和賬單信息

通過填充 requiredBillingAddressFieldsrequiredShippingAddressFields屬性來指定所需賬單信息和配送地址信息。當你顯示一個視圖控制器時,它會提示用戶輸入所需內容。這些字段常量可以像下面這樣進行組合來設置這些屬性:

request.requiredBillingAddressFields = PKAddressFieldEmail;
request.requiredBillingAddressFields = PKAddressFieldEmail | PKAddressFieldPostalAddress;

如果你已經有了用戶的賬單和配送信息,可以直接在支付請求中使用它們。但是盡管Apple Pay默認使用了這些信息,用戶仍然可以在授權支付的過程中修改這些信息

ABRecordRef record = ABPersonCreate();
CFErrorRef error;
BOOL success;
success = ABRecordSetValue(record, kABPersonFirstNameProperty, @"John", &error);
if (!success) {  }
success = ABRecordSetValue(record, kABPersonLastNameProperty, @"Appleseed", &error);
if (!success) {  }
ABMultiValueRef shippingAddress = ABMultiValueCreateMutable(kABMultiDictionaryPropertyType);
NSDictionary *addressDictionary = @{
(NSString *) kABPersonAddressStreetKey: @"1234 Laurel Street",
(NSString *) kABPersonAddressCityKey: @"Atlanta",
(NSString *) kABPersonAddressStateKey: @"GA",
(NSString *) kABPersonAddressZIPKey: @"30303"
};
ABMultiValueAddValueAndLabel(shippingAddress,
(__bridge CFDictionaryRef) addressDictionary,
kABOtherLabel,
nil);
success = ABRecordSetValue(record, kABPersonAddressProperty, shippingAddress, &error);
if (!success) {  }
request.shippingAddress = record;
CFRelease(shippingAddress);
CFRelease(record);
存儲額外信息

使用applicationData屬性來存儲一些在你的應用中關于這次支付請求的唯一標識信息,比如一個購物車的標識符。在用戶授權支付之后,這個屬性的哈希值會出現在這次支付的token中。

part 4 授權支付

支付授權過程是由支付授權view controller和它的代理協作完成的。支付授權view controller做了兩件事情:它讓用戶選擇支付請求所必需的賬單和配送信息,還有讓用戶最終授權同意這次支付。當用戶和view controller交互時,代理方法就會被調用,這樣你的應用就可以不斷地更新顯示的信息--例如在配送地址更改后更新配送費用。用戶最終授權支付請求之后代理方法同樣也會被調用。
注意:在實現這些方法時注意,這些方法可能會被多次調用,而它們被調用的順序取決于用戶的行為的順序。
在所有這個授權過程中被調用的代理方法中,都會有一個completion block被做為參數之一傳入,支付授權view controller會在一個代理方法執行完畢(通過調用completion塊)后再調用另一個代理方法。唯一的例外是paymentAuthorizationViewControllerDidFinish:方法:它不包含completion block,所以它可以在任何時候被調用。
這個completion block有一個傳入參數,基于現有的可用信息,你可以通過這個參數并指定這次交易的狀態。如果這次交易沒有任何問題,傳入PKPaymentAuthorizationStatusSuccess,否則,你要傳入一個識別問題的值。
通過在PKPaymentAuthorizationViewController類的構造方法中傳入一個支付請求來對它進行實例化,然后給這個視圖控制器設置一個代理,就可以把它展示給用戶了。

PKPaymentAuthorizationViewController *viewController = [[PKPaymentAuthorizationViewController alloc] initWithPaymentRequest:request];
if (!viewController) {  }
viewController.delegate = self;
[self presentViewController:viewController animated:YES completion:nil];

當用戶與這個視圖控制器進行交互時,它的代理方法會被調用。

通過代理更新配送方式和費用

當用戶提供配送信息之后,授權view controller 會調用paymentAuthorizationViewController:didSelectShippingAddress:completion: paymentAuthorizationViewController:didSelectShippingMethod:completion:這兩個代理方法。在這兩個方法中根據最新信息來更新支付請求。

- (void) paymentAuthorizationViewController:(PKPaymentAuthorizationViewController *)controller
                   didSelectShippingAddress:(ABRecordRef)address
                                 completion:(void (^)(PKPaymentAuthorizationStatus, NSArray *, NSArray *))completion
{
    self.selectedShippingAddress = address;
    [self updateShippingCost];
    NSArray *shippingMethods = [self shippingMethodsForAddress:address];
    completion(PKPaymentAuthorizationStatusSuccess, shippingMethods, self.summaryItems);
}
  
- (void) paymentAuthorizationViewController:(PKPaymentAuthorizationViewController *)controller
                    didSelectShippingMethod:(PKShippingMethod *)shippingMethod
                                 completion:(void (^)(PKPaymentAuthorizationStatus, NSArray *))completion
{
    self.selectedShippingMethod = shippingMethod;
    [self updateShippingCost];
    completion(PKPaymentAuthorizationStatusSuccess, self.summaryItems);
}
當支付被授權后,支付token會被創建

當用戶最終授權了一個支付請求,框架會通過與蘋果服務器和嵌入在設備中的一個安全模塊進行通信,生成一個支付token。然后你在paymentAuthorizationViewController:didAuthorizePayment:completion:方法中將這個token和其它一些你需要用來處理這次購買的信息--例如配送地址和購物車標識--發送給你的服務器。這個過程是這樣的:

  • 框架發送支付請求給安全模塊,只有安全模塊可以訪問存儲在設備上的標記化的卡信息。
  • 安全模塊把特定的卡和商家等支付數據加密,以保證只有蘋果可以讀取,然后發送給框架。框架會將這些數據發送給蘋果。
  • 蘋果服務器再次加密這些支付數據,以保證只有商家可以讀取。然后服務器對它進行簽名,生成支付token,然后發送給設備。
  • 框架調用相應的代理方法并傳入這個token,然后你的代理方法傳送token給你的服務器。

至于你的服務器采取的行為要取決于你是自己處理這次支付或者你是和其它支付平臺合作來進行支付處理。不管怎樣,你的服務器處理這個訂單然后傳送一個狀態信息給設備,代理方法會把這個狀態信息傳送給completion塊,像在“Processing a Payment”中討論過的。

- (void) paymentAuthorizationViewController:(PKPaymentAuthorizationViewController *)controller
didAuthorizePayment:(PKPayment *)payment
completion:(void (^)(PKPaymentAuthorizationStatus))completion
{
NSError *error;
ABMultiValueRef addressMultiValue = ABRecordCopyValue(payment.billingAddress, kABPersonAddressProperty);
NSDictionary *addressDictionary = (__bridge_transfer NSDictionary *) ABMultiValueCopyValueAtIndex(addressMultiValue, 0);
NSData *json = [NSJSONSerialization dataWithJSONObject:addressDictionary options:NSJSONWritingPrettyPrinted error: &error];
// ... Send payment token, shipping and billing address, and order information to your server ...
PKPaymentAuthorizationStatus status;  // From your server
completion(status);
}
在代理方法中釋放授權View Controller

在框架顯示交易狀態之后,授權View Controller會調用代理paymentAuthorizationViewControllerDidFinish:的方法。在這個方法的實現中,先釋放授權頁面控制器再顯示你自己的訂單確認頁面。

- (void) paymentAuthorizationViewControllerDidFinish:(PKPaymentAuthorizationViewController *)controller
{
[controller dismissViewControllerAnimated:YES completion:nil];
}
Part 5 支付處理

處理一個支付請求涉及以下幾個步驟:

  1. 把支付信息,以及支付流程+所需的其他信息,一起發送給你的服務器。
  1. 驗證支付數據的哈希表和簽名
  2. 為加密過的支付數據解碼
  3. 向支付處理系統提交支付數據
  4. 向訂單追蹤系統提交訂單

處理支付請求時,你有兩個選擇;你既可以利用支付平臺處理支付請求,也可以自己實現支付請求處理流程。一個常用的支付平臺可以完成上述大部分操作。
讀取,驗證,以及處理支付信息需要有一定的相關密碼知識,例如計算SHA-1哈希表,讀取和驗證PKCS#7簽名,執行Elliptic Curve Diffie-Hellman密匙交換。如果沒有一定的密碼學背景,你可以考慮使用第三方支付平臺來完成這些操作。
關于支持Apple Pay支付平臺的更多信息,請參考developer.apple.com/apple-pay/
處理支付請求所用的信息擁有一種嵌套式的數據結構,如下圖。支付令牌是PKPaymentToken類的實例。其paymentData屬性值是一個JSON詞典,它的頭文件信息可以用來驗證和加密支付數據。加密過的數據信息包括支付金額、持卡人姓名,以及一些其他指定的支付處理協議。

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 229,619評論 6 539
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 99,155評論 3 425
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 177,635評論 0 382
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 63,539評論 1 316
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 72,255評論 6 410
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 55,646評論 1 326
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 43,655評論 3 444
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 42,838評論 0 289
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 49,399評論 1 335
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 41,146評論 3 356
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 43,338評論 1 372
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 38,893評論 5 363
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 44,565評論 3 348
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 34,983評論 0 28
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 36,257評論 1 292
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 52,059評論 3 397
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 48,296評論 2 376

推薦閱讀更多精彩內容

  • 1. 配置支付環境 使用XCode創建一個工程, 并設置好對應的BundleID 注冊并配置一個商業標示符 (1)...
    對面來個小胖子閱讀 719評論 0 0
  • 蘋果支付(Apple Pay): Apple Pay,簡單來說, 就是一種移動支付方式。通過Touch ID/ P...
    西風頌閱讀 3,772評論 6 19
  • 步驟1:創建請求文件 步驟2:打開開發者中心 ,找到Merchant IDs,點擊加號,創建一個Merchant ...
    CoderZb閱讀 549評論 0 0
  • 1.About Apple Pay Apple Pay是一種移動支付技術,讓使用者把它們對真實的物品和服務的支付信...
    NEWWORLD閱讀 5,229評論 14 51
  • 關于 Apple Pay apple pay 是一種移動支付技術,它可以讓用戶將自己在現實生活中購物、享受服務的支...
    LuxDark閱讀 542評論 0 2