天天看點

In-App Purchase Programming Guide----(三) ----Retrieving Product InformationRetrieving Product Information

Retrieving Product Information

In the first part of the purchase process, your app retrieves information about its products from the App Store, presents its store UI to the user, and then lets the user select a product, as shown in Figure 2-1.

首先,購買産品時,你的應用程式從應用商店擷取該産品的資訊,把商店UI提供給使用者,然後讓使用者選擇一個産品,如下圖:

Figure 2-1  Stages of the purchase process—displaying store UI

In-App Purchase Programming Guide----(三) ----Retrieving Product InformationRetrieving Product Information

Getting a List of Product Identifiers

一、擷取一個産品識别碼清單

Every product you sell in your app has a unique product identifier. Your app uses these product identifiers to fetch information about products from the App Store, such as pricing, and to submit payment requests when users purchase those products. Your app can either read its list of product identifiers from a file in its app bundle or fetch them from your server. Table 2-1 summarizes the differences between the two approaches.

你在應用程式中出售的每個産品都有一個唯一的産品識别碼。 應用程式使用這些産品識别碼到應用商店擷取産品資訊,比如價格,并在使用者購買這些産品時送出支付請求。 應用程式既可以從它的應用束(bundle)的一個檔案中讀取該産品識别碼清單,也可以從你的伺服器擷取它們。 表2-1 描述了這兩種方法的差別:

Table 2-1  Comparison of approaches for obtaining product identifiers

Embedded in the app bundle Fetched from your server
Used for purchases that Unlock functionality Deliver content
List of products can change When the app is updated At any time
Requires a server No Yes

If your app has a fixed list of products, such as an in-app purchase to remove ads or enable functionality, embed the list in the app bundle. If the list of product identifiers can change without your app needing to be updated, such as a game that supports additional levels or characters, have your app fetch the list from your server.

如果你的應用程式有一個固定的産品清單,比如一個内置購買來移除廣告或開啟功能,就 把清單整合到應用束内。 如果産品識别碼清單不需要應用程式更新就可以做改變,比如一個支援額外關卡或角色的遊戲,可以從你的伺服器擷取清單。

There’s no runtime mechanism to fetch a list of all products configured in iTunes Connect for a particular app. You’re responsible for managing your app’s list of products and providing that information to your app. If you need to manage a large number of products, consider using the bulk XML upload/download feature in iTunes Connect.

沒有運作機制可以為一個特殊的應用擷取iTunes Connect中所有的産品清單。你需要負責管理你的應用程式産品清單并提供該資訊給你的應用程式。如果你需要管理大量的産品,建議使用iTunes Connect中得bulk XML 上傳下載下傳功能。

Embedding Product IDs in the App Bundle

1、在應用束中整合産品IDs

Include a property list file in your app bundle containing an array of product identifiers, such as the following:

在你的應用束中包含了一個特性清單檔案,它包括了一個産品識别碼數組。如下:

<?xml version="1.0" encoding="UTF-8"?>      
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN"      
"http://www.apple.com/DTDs/PropertyList-1.0.dtd">      
<plist version="1.0">      
<array>      
<string>com.example.level1</string>      
<string>com.example.level2</string>      
<string>com.example.rocket_car</string>      
</array>      
</plist>      

To get product identifiers from the property list, locate the file in the app bundle and read it.

要想從plist檔案中擷取産品識别碼,在應用束中找到該檔案并讀取它。

NSURL *url = [[NSBundle mainBundle] URLForResource:@"product_ids"      
withExtension:@"plist"];      
NSArray *productIdentifiers = [NSArray arrayWithContentsOfURL:url];      

Fetching Product IDs from Your Server

2、從伺服器擷取産品IDs

Host a JSON file on your server with the product identifiers. For example:

上傳一個JSON檔案到你的伺服器,檔案裡帶有産品識别碼:如下:

[      
"com.example.level1",      
"com.example.level2",      
"com.example.rocket_car"      
]      

To get product identifiers from your server, fetch and read the JSON file as shown in Listing 2-1. Consider versioning the JSON file so that future versions of your app can change its structure without breaking older versions of your app. For example, you could name the file that uses the old structure 

products_v1.json

and the file that uses a new structure 

products_v2.json

. This is especially useful if your JSON file is more complex than the simple array in the example.

要想從伺服器擷取産品識别碼,如清單2-1所示擷取并讀取該JSON檔案。 考慮JSON 檔案的版本化,這樣應用程式的未來版本就可以随時改變它的結構,而不需要打破應用程式的老版本。比如,你可以把使用老結構的産品命名為_v1.json, 把使用新結構的檔案命名為_v2.json. 如果你的JSON檔案比示例中的簡單數組更複雜時,版本化方法更加有用。

Listing 2-1  Fetching product identifiers from your server

- (void)fetchProductIdentifiersFromURL:(NSURL *)url delegate:(id)delegate      
{      
dispatch_queue_t global_queue =      
dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);      
dispatch_async(global_queue, ^{      
NSError *err;      
NSData *jsonData = [NSData dataWithContentsOfURL:url      
options:NULL      
error:&err];      
if (!jsonData) { /* Handle the error */ }      
NSArray *productIdentifiers = [NSJSONSerialization      
JSONObjectWithData:jsonData options:NULL error:&err];      
if (!productIdentifiers) { /* Handle the error */ }      
dispatch_queue_t main_queue = dispatch_get_main_queue();      
dispatch_async(main_queue, ^{      
[delegate displayProducts:productIdentifiers]; // Custom method      
});      
});      
}      

For information about downloading files using 

NSURLConnection

, see “Using NSURLConnection” in URL Loading System Programming Guide.

更多關于使用 

NSURLConnection

下載下傳檔案的資訊,請看“Using NSURLConnection” in URL Loading System Programming Guide.

To ensure that your app remains responsive, use a background thread to download the JSON file and extract the list of product identifiers. To minimize the data transferred, use standard HTTP caching mechanisms, such as the 

Last-Modified

 and 

If-Modified-Since

 headers.

為了確定你的應用程式保持響應,使用一個背景線程來下載下傳JSON檔案,并提取産品識别碼清單。 要想最小化資料轉換,使用标準的HTTP緩存機制,比如Last-Modified 和  If-Modified-Since 頭。

Retrieving Product Information

二、取回産品資訊

To make sure your users see only products that are actually available for purchase, query the App Store before displaying your app’s store UI.

為了確定你的使用者隻看到真實可買的産品,在顯示應用的商店UI之前查詢應用商店。

Use a products request object to query the App Store. First, create an instance of 

SKProductsRequest

 and initialize it with a list of product identifiers. The products request retrieves information about valid products, along with a list of the invalid product identifiers, and then calls its delegate to process the result. The delegate must implement the 

SKProductsRequestDelegate

 protocol to handle the response from the App Store. Listing 2-2 shows a simple implementation of both pieces of code.

使用一個産品請求對象來查詢應用商店。首先,建立一個 

SKProductsRequest

  執行個體,并用産品識别碼清單初始化它。 産品請求取回有效産品的資訊,以及一個有效産品識别碼清單,然後調用它的委托來處理結果。 委托必須實作 

SKProductsRequestDelegate

  協定來處理從應用商店的響應。 清單2-2 現實了一個兩段代碼的簡單實作。

Listing 2-2  Retrieving product information

// Custom method      
- (void)validateProductIdentifiers:(NSArray *)productIdentifiers      
{      
SKProductsRequest *productsRequest = [[SKProductsRequest alloc]      
initWithProductIdentifiers:[NSSet setWithArray:productIdentifiers]];      
productsRequest.delegate = self;      
[productsRequest start];      
}      
// SKProductsRequestDelegate protocol method      
- (void)productsRequest:(SKProductsRequest *)request      
didReceiveResponse:(SKProductsResponse *)response      
{      
self.products = response.products;      
for (NSString *invalidIdentifier in response.invalidProductIdentifiers) {      
// Handle any invalid product identifiers.      
}      
[self displayStoreUI]; // Custom method      
}      

When the user purchases a product, you need the corresponding product object to create a payment request, so keep a reference to the array of product objects that’s returned to the delegate. If the list of products your app sells can change, you may want to create a custom class that encapsulates a reference to the product object as well as other information—for example, pictures or description text that you fetch from your server. Payment requests are discussed in“Requesting Payment.”

當使用者購買一個産品時,你需要給該産品對象提供一個支付請求,是以保留一個到産品對象數組的引用,該數組會被傳回給委托。 如果你的應用出售的産品清單能改變,你或許想要建立一個自定義類來把一個引用和其它資訊一起封裝到産品對象中---比如, 圖檔或你從伺服器擷取的描述文本。 支付請求在“Requesting Payment.” 中讨論。

Product identifiers being returned as invalid usually indicates an error in your app’s list of product identifiers, although it could mean the product hasn’t been properly configured in iTunes Connect. Good logging and a good UI help you resolve this type of issue more easily. In production builds, your app needs to fail gracefully—typically, this means displaying the rest of your app’s store UI and omitting the invalid product. In development builds, display an error to call attention to the issue. In both production and development builds, use 

NSLog

 to write a message to the console so you have a record of the invalid identifier. If your app fetched the list from your server, you could also define a logging mechanism to let your app send the list of invalid identifiers back to your server.

傳回的無效産品識别碼通常表明應用産品識别碼清單中發生了一個error, 盡管它或許意味着該産品在iTunes Connect中沒有被正确配置。良好的日志(logging)和一個好的UI可以幫你更簡單地解決該類型的問題。 在産品建構中,你的應用需要優雅地失敗---通常,這意味着顯示剩餘的應用UI以及忽略無效産品。 在開發建構中,顯示一個error來引起對該問題的關注。 在産品和開發建構中,都使用 

NSLog

  來編寫一個消息(message)來解決,這樣你就有一個無效識别碼的記錄。 如果你的應用從伺服器擷取清單,你或許還要定義一個日志機制來讓你的應用程式把無效識别碼發送回伺服器。

Presenting Your App’s Store UI

三、呈現你的應用商店UI

Because the design of your app’s store has an important impact on your in-app sales, it’s worth investing the time and effort to get it right. Design the user interface for your store UI so it integrates with the rest of your app. Store Kit can’t provide a store UI for you. Only you know your app and its content well enough to design your store UI in a way that showcases your products in their best light and fits seamlessly with the rest of your app.

因為你的應用的商店設計對你的内置銷售有很重要的影響,是以它值得投入時間和精力讓其順利工作。 為你的商店UI設計使用者界面讓它與你的應用的剩餘部分內建(integrates)。 商店Kit 不能給你提供商店UI。 隻有充分了解你的應用和它的内容設計出來的商店UI,才能以最佳方向展示你得産品并使它與你的應用無縫結合。

Consider the following guidelines as you design and implement your app’s store UI.

當你設計和實作應用商店的UI時,請考慮以下指南:

Display a store only if the user can make payments. To determine whether the user can make payments, call the 

canMakePayments

 class method of the

SKPaymentQueue

 class. If the user can’t make payments (for example, because of parental restrictions), either display UI indicating that that the store isn’t available or omit the store portion of your UI entirely.

1. 隻在使用者可以支付時顯示一個商店。 調用

SKPaymentQueue

  類 的canMakePayment 方法來确認使用者是否可以支付。 如果使用者不能支付(比如,父母限制), 可以顯示UI表明一個商店不可用,或者完全忽略商店部分。

Present products naturally in the flow of your app. Find the best place in your UI to show your app’s store UI. Present products in context at the time when the user can use them—for example, let users unlock functionality when they try to use that premium feature. Pay special attention to the experience a user has when exploring your app for the first time.

2. 在你的應用流(flow)中自然地呈現産品。 在你的UI找到最好的位置來顯示你的應用商店UI。 在使用者可以使用它們的時候呈現産品---比如,當使用者嘗試使用進階功能時讓使用者解鎖該功能。 特别關注使用者第一次使用你的應用時的使用者體驗。

Organize products so that exploration is easy and enjoyable. If your app has a small enough number of products, you can display everything on one screen; otherwise, group or categorize products to make them easy to navigate. Apps with a large number of products, such as comic book readers or magazines with many issues, benefit especially from an interface that makes it easy for users to discover new items they want to purchase. Make the differences between your products clear by giving them distinct names and visuals—if necessary, include explicit comparisons.

3. 組織産品,這樣探索就變得既簡單又愉快。 如果你的應用隻有一點産品,你可以在一個螢幕上顯示所有産品;否則就把産品分組或分類讓使用者可以容易找到。 帶有大數量産品的應用,比如,漫畫書或者有很多報道的雜志,制作一個可以讓使用者簡單地發現它們想要購買的新産品會特别有用。 給你的産品一個不同的名字和視覺效果,明确地區分它們--如有需要,包括明确地比較。

Communicate the value of your products to your users. Users want to know exactly what they’re going to buy. Combine information from the App Store, such as product prices and descriptions, with additional data from your server or the app bundle, such as images or demos of your products. Let users interact with a product in a limited way before buying it. For example, a game that gives the user the option to buy new race cars can allow users to run a test lap with the new car. Likewise, a drawing app that lets the user buy additional brushes can give users the chance to draw with the new brush on a small scratch pad and see the difference between brushes. This kind of design provides users an opportunity to experience the product and be convinced they want to purchase it.

4、向使用者交流你的産品的價值。 使用者想要準确地知道他們即将要買什麼。 綜合應用商店的資訊,比如産品價格和描述,和伺服器或應用束中的附加資料,比如,産品的圖檔或demos。 讓使用者在購買之前以一種限制的方式展現産品。 舉個例子,有一個遊戲,讓使用者選擇購買新賽車(race cars)可以讓使用者用新車試跑一圈。 又或者,一個繪圖應用,讓使用者購買一個額外的筆刷可以讓使用者用新筆刷在一個小便簽上繪圖,讓它檢視筆刷之間的差別。 這類的設計給使用者提供了一個體驗産品的機會并說服它們購買。

Display prices clearly, using the locale and currency returned by the App Store. Ensure that the price of a product is easy to find and easy to read. Don’t try to convert the price to a different currency in your UI, even if the user’s locale and the price’s locale differ. Consider, for example, a user in the United States who prefers the United Kingdom locale for its units and date formatting. Your app displays its UI according to the United Kingdom locale, but it still needs to display product information in the locale specified by the App Store. Converting prices to British pounds sterling, in an attempt to match the United Kingdom locale of the rest of the interface, would be incorrect. The user has an App Store account in the United States and pays in U.S. dollars, so prices would be provided to your app in U.S. dollars. Likewise, your app would display its prices in U.S. dollars. Listing 2-3 shows how to correctly format a price by using the product’s locale information.

5、使用應用商店傳回的語言環境(locale)和貨币清楚地顯示價格。 確定能簡單找到産品的價格并能簡單地識别。 不要嘗試在你的UI中把價格轉換為一個不同的貨币,即使使用者的語言環境和價格的語言環境不一樣。 想想看,一個在美國的使用者因為它的機關和日期格式更喜歡英國的語言環境。 你的應用根據英國的語言環境顯示它的UI,但它任然需要用應用商店指定的語言環境顯示産品資訊。 為了嘗試比對餘下界面的英國語言環境,把價格轉換為英國英鎊是不正确的。 使用者在美國有一個應用商店賬号,它用美元支付,是以會給你的應用提供一個以美元為機關的價格。還有,你得應用将以美元為單元顯示價格。清單2-3 顯示了如何通過使用産品的語言環境資訊來正确設定價格機關。

Listing 2-3  Formatting a product’s price

NSNumberFormatter *numberFormatter = [[NSNumberFormatter alloc] init];      
[numberFormatter setFormatterBehavior:NSNumberFormatterBehavior10_4];      
[numberFormatter setNumberStyle:NSNumberFormatterCurrencyStyle];      
[numberFormatter setLocale:product.priceLocale];      
NSString *formattedPrice = [numberFormatter stringFromNumber:product.price];      

After a user selects a product to buy, your app connects to the App Store to request payment for the product.

當使用者選擇好要購買的産品後,你的應用連接配接到應用商店請求為該産品提供支付。

Suggested Testing Steps

四、建議測試步驟

Test each part of your code to verify that you’ve implemented it correctly.

測試代碼的每個部分來認證你已經正确地實作了該功能。

Sign In to the App Store with Your Test Account

1、用你的測試賬号登入應用商店

Create a test user account in iTunes Connect, as described in “Creating Test User Accounts” in iTunes Connect Developer Guide.

在iTunes Connect裡建立一個測試賬号,請看 iTunes Connect Developer Guide 的“Creating Test User Accounts” 。

On a development iOS device, sign out of the App Store in Settings. Then build and run your app from Xcode.

在一個iOS開發裝置中,在設定中退出應用商店。然後從Xcode建構和運作你的應用。

On a development OS X device, sign out of the Mac App Store. Then build your app in Xcode and launch it from the Finder.

在一個OS X開發裝置中,退出Mac 應用商店。 然後在Xcode中建構你的應用,并從Finder中運作它。

Use your app to make an in-app purchase. When prompted to sign in to the App Store, use your test account. Note that the text “[Environment: Sandbox]” appears as part of the prompt, indicating that you’re connected to the test environment.

使用你的應該來完成一個内置購買。當提示你登陸應用商店時,使用你的測試賬号。 注意提示框中出現的[Environment: Sandbox]文字提示你目前連接配接到測試環境。

If the text “[Environment: Sandbox]” doesn’t appear, you’re using the production environment. Make sure you’re running a development-signed build of your app. Production-signed builds use the production environment.

如果[Environment: Sandbox] 沒有出現,則表示你使用的是産品環境。 確定你的應用運作在一個開發簽署(development-signed)建構。簽署的産品建構使用産品環境。

Important: Don’t use your test user account to sign in to the production environment. If you do, the test user account becomes invalid and can no longer be used.

 重要提示:不要用你的測試使用者賬号登陸産品環境,否則測試使用者賬号将無效不能再使用。

Test Fetching the List of Product Identifiers

2. 測試擷取産品認證碼清單

If your product identifiers are embedded in your app, set a breakpoint in your code after they’re loaded and verify that the instance of 

NSArray

 contains the expected list of product identifiers.

如果你的産品認證碼被整合進應用程式,在它們加載後,在代碼裡設定一個斷點,并認證包含了預期産品識别碼清單的NSArray執行個體。

If your product identifiers are fetched from a server, manually fetch the JSON file—using a web browser such as Safari or a command-line utility such as 

curl

—and verify that the data returned from your server contains the expected list of product identifiers. Also verify that your server correctly implements standard HTTP caching mechanisms.

如果你的産品識别碼是從伺服器中擷取的,使用一個網絡浏覽器如Safari或一個指令行工具如curl來手工擷取JSON檔案,并認證從伺服器傳回的資料,該資料包含了預期的産品識别碼清單。 同時還要認證你得伺服器正确地實作了标準HTTP緩存機制。

Test Handling of Invalid Product Identifiers

3、測試處理無效産品識别碼

Intentionally include an invalid identifier in your app’s list of product identifiers. (Make sure you remove it after testing.)

在你的産品識别碼清單中故意包含進一個無效識别碼。(確定在測試成功後删除它)

In a production build, verify that the app displays the rest of its store UI and users can purchase other products. In a development build, verify that the app brings the issue to your attention.

在一個産品建構中,驗證應用程式顯示了其餘的商店UI,使用者可以購買其他的産品。 在一個開發建構中,驗證應用程式中引起你關注的問題。

Check the console log and verify that you can correctly identify the invalid product identifier.

檢查控制台日志并驗證你可以正确地識别無效産品識别碼。

Test a Products Request

4、測試一個産品請求

Using the list of product identifiers that you tested, create and submit an instance of 

SKProductsRequest

. Set a breakpoint in your code, and inspect the lists of valid and invalid product identifiers. If there are invalid product identifiers, review your products in iTunes Connect and correct your JSON file or property list.

使用你測試好的産品識别碼清單,建立并遞交一個

SKProductsRequest 執行個體。 在你的代碼中設定一個斷點,檢查有效和無效的産品識别碼。 如果有無效産品識别碼,檢閱iTunes Connect中的産品并更正你的JSON檔案或特性清單。

下一頁      上一頁

轉載于:https://www.cnblogs.com/patientAndPersist/p/3701978.html