這篇文檔翻譯自apple,appstore的購買部分。主要介紹的是訂閱功能,包括普通訂閱和自動訂閱。文檔本身沒有介紹詳細的API payload,沒有demo。我看的不是很明白,所以把它逐字翻譯,便於理解。
提供訂閱的App,需要一些考慮一些額外的行為。因為訂閱涉及了時間,你的app必須能夠確定訂閱是否當前有效,或者訂閱已經過期。你的app也必須能夠相應訂閱的創建,續期,以及過期,並且能夠合理的處理過期訂閱。
下圖解釋了訂閱的時間線,包括你app需要處理的一些復雜東西:
計算訂閱的有效期
你的app需要能夠決定,某些內容只有在用戶的訂閱有效時才能夠訪問。例如,一個用戶訂閱了一個月的雜志,這個雜志在每月1號發布,你需要考慮下表的情況:
時間 | 事件 | 訂閱狀態 |
---|---|---|
2月1日 | 二月雜志發布。用戶不可獲得,因為他現在還沒有訂閱 | 未訂閱 |
2月20日 | 用戶訂閱了雜志的閱讀觀看計划。二月份的雜志因為是最近的,所以用戶可以立即觀看 | 激活 |
3月1日 | 三月份的雜志發布了。用戶可以立即獲得,因為他的訂閱還在有效期內 | 激活 |
3月20日 | 用戶的訂閱,自動更新了 | 激活 |
4月1日 | 四月份的雜志發布了。用戶可以立即獲得,因為他的訂閱還在有效期內 | 激活 |
4月20日 | 用戶取消了訂閱,所以訂閱周期結束了 | 過期 |
5月1日 | 五月份的雜志發布了。用戶不能獲取,因為他的訂閱已經過期 | 過期 |
6月1日 | 六月份的雜志發布了。用戶不能獲取,因為他的訂閱已經過期 | 過期 |
6月17日 | 用戶訂閱了。六月份的雜志可以立即觀看 | 激活 |
7月1日 | 七月份的雜志發布了。用戶可以立即獲得,因為他的訂閱還在有效期內 | 激活 |
想要為用戶提供所有可訪問內容的權限,就需要在每次內容發布的時候都記錄日期。需要根據每個收據的Original Purchase Date
, Purchase Date
和Subscription Expiration Date
來確定訂閱周期的開始和結束時間(關於recipe的信息,請參考這篇文檔)。用戶可以在訂閱的開始時間到結束時間之間的時間范圍內,訪問所有已經發布的內容,內容需要在用戶購買訂閱后立即解鎖。
想要確定訂閱的過期,需要通過對比每個收據的Subscription Expiration Date
和Purchase Date
字段。
注意:請不要通過在購買日期后加上訂閱時間的方式來計算訂閱周期。這個方法,沒有考慮到免費試用期,營銷免費期。
例如,因為用戶購買訂閱后內容總是會被解鎖,一個用戶如果在一個月中旬購買了一個總是在月初發布的雜志,那么他在初次訂閱的時候是可以訪問兩個月份的發布雜志的。包括他購買時那個月份的雜志,以及下個月初發布的那份雜志。
接着上面的圖表來說,收據可以顯示下面的日期范圍:
- 2月20日 - 3月20日
- 3月20日 - 4月20日
- (過期的4月20日 - 6月17日 不會顯示在收據中)
- 6月17日 - 7月17日
用戶可以訪問2月和6月的雜志,因為他在這些個月份完成了購買,那么就需要解鎖。
用戶可以訪問3月,4月,6月和7月,因為這些時間段的時候訂閱都處於激活狀態。
(訂閱)計划的升級和變更
用戶可以在App Store中或者你的UI中管理他的訂閱。對於每個訂閱,App Store都會提供訂閱提供方提供的續期選項。用戶可以很簡便的選擇修改他的服務等級,選擇升級,降級,或者跨等級修改。降級和跨級別修改,可以在下一次續期時生效。
過期和續期
訂閱續期程序,會在訂閱過期的前十天開始。在這些天中,App Store會檢查用戶不能完成自動續約的賬單問題,例如:
- 用戶的付款方式不在激活狀態
- 商品在用戶的訂閱期中進行了提價
- 商品已經下架
App Store如果遇到問題,會對用戶進行提示,以免影響到他們的訂閱服務。
在訂閱過期前的24小時,App Store會開始嘗試進行續期。App Store會進行若干次續期嘗試,但是如果失敗太多,則會終止自動更新。
注意:對於賬單相關的問題,App Store可能會在60天之前就開始進行續期嘗試。你可以通過收據中的
Subscription Retry
字段來確定是否是這個情況。
App Store會在訂閱過期之前,毫無痕跡的完成續期,以免用戶面對訂閱過期問題。不過,過期還是有可能的。例如,如果用戶的支付信息無效,第一次需求嘗試會失敗。如果用戶在訂閱過期之后,更新了他的支付信息,那么在這中間的一小段時間中,用戶就處於訂閱過期狀態。用戶也可以取消自動需求,或者有意讓訂閱過期,之后一段時間再繼續續訂,那么就會有一段較長時間的過期。請確定你的App可以處理這些過期情況。
在一個訂閱成功續期之后,StoreKit會將一個續期交易加入到交易隊列中。你的app需要檢查和處理交易隊列。請注意,如果你的app在訂閱更新的時候已經開始運行,那么交易observer不會被調用;app必須重新啟動才行。
作為例子,下面的時間線表格展示了一個用戶的賬號訂閱了一個app提供的月度服務計划。在這個例子中,訂閱曾經因為賬單問題,存在了短暫的過期。用戶隨后糾正了訂單問題,訂閱隨后被續訂。
日期 | 事件 | 訂閱狀態 |
---|---|---|
2月20日 | 用戶訂閱了月度訂閱。服務立即可用。 | 激活 |
3月20日 | 用戶的訂閱成功自動續期。服務仍然可用。 | 激活 |
4月19日 | 用戶的支付方式過期了。 | 激活 |
4月20日 | 因為交易失敗,用戶的自動續期也失敗了。訂閱過期了 | 過期 |
5月5日 | 用戶更新了他的支付方式。App Store可以從新發起訂閱續期。服務立即可用 | 激活 |
6月5日 | 用戶的訂閱成功自動續期。服務仍然可用。 | 激活 |
取消
因為訂閱在購買的時候是全額付款。用戶只有在聯系Apple消費者支持的時候才能取回退款。例如,如果用戶意外的買錯一件商品,消費者支持可以取消這次購買,並且對用戶進行完全或部分退款。消費者可能在一個訂閱的途中取消了訂閱,但是這個訂閱已經被支付了,它必須完成之前承諾的服務直到過期。
想要檢查是否一次購買交易已經由Apple消費者支持取消,可以通過檢查收據中的Cancellation Date
來完成。如果這個字段包含一個日期,那么不管過期日期,這次購買都被取消了。處理被取消的購買,應該像這次購買從來沒發生一樣。
狀態更新提醒
StatusUpdateNotification
是一個服務器-服務器的提醒服務,專門用來處理訂閱的自動續訂。這個提醒會在發送的時候,聲明訂閱的狀態。
想要獲得你處理事件的最新信息,你的app需要驗證App Store中的最后一條收據。強烈推薦你使用狀態更新提醒和收據驗證功能來驗證一個用戶當前的訂閱狀態,並對他們提供服務。
想要接受狀態更新提醒,你需要在Apple的后台配置訂閱狀態URL。App Store會通過HTTP(S) POST請求,將數據以JSON的形式發送到你的服務器。你的服務器應該負責解析,解釋,以及響應所有的 statusUpdateNotification
請求。
使用服務器-服務器提醒服務不是必須的,你可以在任何時候選擇使用它。
statusUpdateNotification
是一個HTTP POST請求,它的請求提包含下列元素:
Key | 描述 |
---|---|
environment | 指明這個提醒來自沙盒或者生產環境:Sandbox PROD |
notification_type | 描述這個提醒的類型。詳情見下面的提醒類型表 |
password | 這個值和你驗證收據是用的shared secret是一樣的 |
original_transaction_id | 這個值和收據中的Original Transaction Identifier是一樣的。你可以使用這個值來為單個用戶訂閱關聯多個IOS 6風格的交易手機 |
cancellation_date | Apple消費者支持取消交易的日期。只有在notification_type 是CANCEL 的時候才會存在 |
web_order_line_item_id | 用來標示訂閱購買的主鍵。只有在notification_type 是CANCEL 的時候才會存在 |
latest_receipt | base64編碼的交易收據receipt。只有在notification_type 為RENEWAL 或者INTERACTIVE_RENEWAL 的時候才會有,並且只有在續訂成功的時候才會有。 |
latest_receipt_info | 最近receipt的信息,以JSON表示。只有在續訂成功的時候才會有。 |
latest_expired_receipt | base64編碼的交易收據receipt。只有在訂單過期的時候才會收到。 |
latest_expired_receipt_info | 最近receipt的信息,以JSON表示。只有在訂單過期的時候才會收到。 |
auto_renew_status | 一個布爾值,true或者false。和receipt中的auto renew status 一樣 |
auto_renew_adam_id | 自動訂閱當前的續訂優先級。這是商品的Apple ID。 |
auto_renew_product_id | 這個字段和receipt中的Subscription Auto Renew Perference 一樣 |
expiration_intent | 這個字段和receipt中的Subscription Expiration Intent 一樣。只有在notification_type 為RENEWAL 或者INTERACTIVE_RENEWAL 的時候才有. |
下面是提醒類型的列表:
提醒類型 | 描述 |
---|---|
INITIAL_BUY | 初次購買訂閱。請將latest_receipt 存儲在你的服務器,隨時可以當作token來驗證,以確定用戶的訂閱狀態。 |
CANCEL | 訂閱已經由Apple消費者支持所取消。請檢查Cancellation Date 字段來確定何時訂閱被取消。 |
RENEWAL | 一個已過期的訂閱被成功地自動續訂。請檢查Subscription Expiration Date 來確定下一個續訂的日期和時間。 |
INTERACTIVE_RENEWAL | 在訂閱過期之后,用戶手動選擇了續訂,可以是在你的App UI中操作,或者在Apple Store的用戶設置中操作。續訂后服務應該立即可用。 |
DID_CHANGE_RENEWAL_PREF | 用戶修改了訂閱計划,在下一個訂閱周期的時候生效。當前生效的訂閱計划不受影響。 |
為了確認statusUpdateNotification
請求成功被處理,你的服務器應該返回200的響應;不需要返回任何的數據。如果你的服務器返回50x或者40x的響應碼,App Store會重新發送這個提醒。
安全要求
在發送提醒之前,Apple Store會使用ATS協議(App Transport Security)對你的服務器建立安全連接。如果安全連接不可建立,那么提醒就不能發送到你的服務器。
測試環境中的狀態更新提醒
強烈推薦在部署到生產環境之前,將你的statusUpdateNotification
處理邏輯在測試環境經過測試。
跨平台考慮
商品標識符只關聯單個app。擁有IOS和MacOS的App應該分別由單獨的商品,每個平台應該有單獨的商品標識。你可以讓在IOS App中訂閱的用戶,同樣可以訪問MacOS的內容,但是具體的實現應該是你自己的責任。
讓你的用戶可以管理訂閱
除了實現你自己的訂閱管理UI,你的App頁可以打開下面的URL:
https://buy.itunes.apple.com/WebObjects/MZFinance.woa/wa/manageSubscriptions
打開這個URL,會開啟iTunes或者iTunes Store,並且打開訂閱頁面。
測試環境
測試環境和生產環境之間,對於自動續期訂閱存在不同的處理方式。
在測試環境中,訂閱續期的發生速率需要提升,自動續訂每天最多可以發生6次。這樣可以讓你充分驗證一個訂閱的續訂,訂閱的失效。。。
因為訂閱的過期和續訂率提速了,訂閱可以在系統續訂前過期,在訂閱周期中留下一段失效期。請確保你的app能夠正確處理這種情況。