鍍金池/ 教程/ iOS/ 獲取產(chǎn)品信息
恢復(fù)購(gòu)買(mǎi)記錄
內(nèi)置購(gòu)買(mǎi)
介紹
準(zhǔn)備應(yīng)用程序?qū)彶?/span>
創(chuàng)建和配置產(chǎn)品
獲取產(chǎn)品信息
支付請(qǐng)求
使用訂閱
如何測(cè)試應(yīng)用程序內(nèi)置購(gòu)買(mǎi)
產(chǎn)品交付

獲取產(chǎn)品信息

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.

首先,購(gòu)買(mǎi)產(chǎn)品時(shí),你的應(yīng)用程序從應(yīng)用商店獲取該產(chǎn)品的信息,把商店 UI 提供給用戶,然后讓用戶選擇一個(gè)產(chǎn)品,如下圖:

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

http://wiki.jikexueyuan.com/project/in-app-purchase/images/4.png" alt="" />

Getting a List of Product Identifiers

一、獲取一個(gè)產(chǎn)品識(shí)別碼列表

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.

你在應(yīng)用程序中出售的每個(gè)產(chǎn)品都有一個(gè)唯一的產(chǎn)品識(shí)別碼。 應(yīng)用程序使用這些產(chǎn)品識(shí)別碼到應(yīng)用商店獲取產(chǎn)品信息,比如價(jià)格,并在用戶購(gòu)買(mǎi)這些產(chǎn)品時(shí)提交支付請(qǐng)求。 應(yīng)用程序既可以從它的應(yīng)用束(bundle)的一個(gè)文件中讀取該產(chǎn)品識(shí)別碼列表,也可以從你的服務(wù)器獲取它們。表2-1 描述了這兩種方法的區(qū)別:

Table 2-1 Comparison of approaches for obtaining product identifiers

http://wiki.jikexueyuan.com/project/in-app-purchase/images/5.png" alt="" />

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.

如果你的應(yīng)用程序有一個(gè)固定的產(chǎn)品列表,比如一個(gè)內(nèi)置購(gòu)買(mǎi)來(lái)移除廣告或開(kāi)啟功能,就 把列表整合到應(yīng)用束內(nèi)。 如果產(chǎn)品識(shí)別碼列表不需要應(yīng)用程序更新就可以做改變,比如一個(gè)支持額外關(guān)卡或角色的游戲,可以從你的服務(wù)器獲取列表。

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.

沒(méi)有運(yùn)行機(jī)制可以為一個(gè)特殊的應(yīng)用獲取 iTunes Connect 中所有的產(chǎn)品列表。你需要負(fù)責(zé)管理你的應(yīng)用程序產(chǎn)品列表并提供該信息給你的應(yīng)用程序。如果你需要管理大量的產(chǎn)品,建議使用 iTunes Connect 中得 bulk XML 上傳下載功能。

Embedding Product IDs in the App Bundle

1、在應(yīng)用束中整合產(chǎn)品 IDs

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

在你的應(yīng)用束中包含了一個(gè)特性列表文件,它包括了一個(gè)產(chǎn)品識(shí)別碼數(shù)組。如下:

<?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 文件中獲取產(chǎn)品識(shí)別碼,在應(yīng)用束中找到該文件并讀取它。

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

Fetching Product IDs from Your Server

2、從服務(wù)器獲取產(chǎn)品 IDs

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

上傳一個(gè) JSON 文件到你的服務(wù)器,文件里帶有產(chǎn)品識(shí)別碼:如下:

[
    "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.jsonand 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.

要想從服務(wù)器獲取產(chǎn)品識(shí)別碼,如列表2-1所示獲取并讀取該 JSON 文件。 考慮 JSON 文件的版本化,這樣應(yīng)用程序的未來(lái)版本就可以隨時(shí)改變它的結(jié)構(gòu),而不需要打破應(yīng)用程序的老版本。比如,你可以把使用老結(jié)構(gòu)的產(chǎn)品命名為_(kāi)v1.json, 把使用新結(jié)構(gòu)的文件命名為_(kāi)v2.json. 如果你的 JSON 文件比示例中的簡(jiǎn)單數(shù)組更復(fù)雜時(shí),版本化方法更加有用。

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.

更多關(guān)于使用 NSURLConnection 下載文件的信息,請(qǐng)看 “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.

為了確保你的應(yīng)用程序保持響應(yīng),使用一個(gè)后臺(tái)線程來(lái)下載 JSON 文件,并提取產(chǎn)品識(shí)別碼列表。 要想最小化數(shù)據(jù)轉(zhuǎn)換,使用標(biāo)準(zhǔn)的HTTP緩存機(jī)制,比如 Last-Modified 和 If-Modified-Since 頭。

Retrieving Product Information

二、取回產(chǎn)品信息

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.

為了確保你的用戶只看到真實(shí)可買(mǎi)的產(chǎn)品,在顯示應(yīng)用的商店 UI 之前查詢應(yīng)用商店。

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.

使用一個(gè)產(chǎn)品請(qǐng)求對(duì)象來(lái)查詢應(yīng)用商店。首先,創(chuàng)建一個(gè) SKProductsRequest 實(shí)例,并用產(chǎn)品識(shí)別碼列表初始化它。 產(chǎn)品請(qǐng)求取回有效產(chǎn)品的信息,以及一個(gè)有效產(chǎn)品識(shí)別碼列表,然后調(diào)用它的委托來(lái)處理結(jié)果。 委托必須實(shí)現(xiàn) SKProductsRequestDelegate 協(xié)議來(lái)處理從應(yīng)用商店的響應(yīng)。列表2-2現(xiàn)實(shí)了一個(gè)兩段代碼的簡(jiǎn)單實(shí)現(xiàn)。

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.”

當(dāng)用戶購(gòu)買(mǎi)一個(gè)產(chǎn)品時(shí),你需要給該產(chǎn)品對(duì)象提供一個(gè)支付請(qǐng)求,因此保留一個(gè)到產(chǎn)品對(duì)象數(shù)組的引用,該數(shù)組會(huì)被返回給委托。 如果你的應(yīng)用出售的產(chǎn)品列表能改變,你或許想要?jiǎng)?chuàng)建一個(gè)自定義類來(lái)把一個(gè)引用和其它信息一起封裝到產(chǎn)品對(duì)象中---比如, 圖片或你從服務(wù)器獲取的描述文本。 支付請(qǐng)求在“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.

返回的無(wú)效產(chǎn)品識(shí)別碼通常表明應(yīng)用產(chǎn)品識(shí)別碼列表中發(fā)生了一個(gè) error, 盡管它或許意味著該產(chǎn)品在 iTunes Connect 中沒(méi)有被正確配置。良好的日志(logging)和一個(gè)好的 UI 可以幫你更簡(jiǎn)單地解決該類型的問(wèn)題。 在產(chǎn)品構(gòu)建中,你的應(yīng)用需要優(yōu)雅地失敗---通常,這意味著顯示剩余的應(yīng)用 UI 以及忽略無(wú)效產(chǎn)品。 在開(kāi)發(fā)構(gòu)建中,顯示一個(gè) error 來(lái)引起對(duì)該問(wèn)題的關(guān)注。在產(chǎn)品和開(kāi)發(fā)構(gòu)建中,都使用 NSLog 來(lái)編寫(xiě)一個(gè)消息(message)來(lái)解決,這樣你就有一個(gè)無(wú)效識(shí)別碼的記錄。 如果你的應(yīng)用從服務(wù)器獲取列表,你或許還要定義一個(gè)日志機(jī)制來(lái)讓你的應(yīng)用程序把無(wú)效識(shí)別碼發(fā)送回服務(wù)器。

Presenting Your App’s Store UI

三、呈現(xiàn)你的應(yīng)用商店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.

因?yàn)槟愕膽?yīng)用的商店設(shè)計(jì)對(duì)你的內(nèi)置銷(xiāo)售有很重要的影響,因此它值得投入時(shí)間和精力讓其順利工作。 為你的商店 UI 設(shè)計(jì)用戶界面讓它與你的應(yīng)用的剩余部分集成(integrates)。 商店 Kit 不能給你提供商店 UI。 只有充分了解你的應(yīng)用和它的內(nèi)容設(shè)計(jì)出來(lái)的商店 UI,才能以最佳方向展示你得產(chǎn)品并使它與你的應(yīng)用無(wú)縫結(jié)合。

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

當(dāng)你設(shè)計(jì)和實(shí)現(xiàn)應(yīng)用商店的 UI 時(shí),請(qǐng)考慮以下指南:

Display a store only if the user can make payments. To determine whether the user can make payments, call the canMakePayments class method of theSKPaymentQueue 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.只在用戶可以支付時(shí)顯示一個(gè)商店。 調(diào)用 SKPaymentQueue 類 的canMakePayments 方法來(lái)確認(rèn)用戶是否可以支付。 如果用戶不能支付(比如,父母限制), 可以顯示 UI 表明一個(gè)商店不可用,或者完全忽略商店部分。

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.在你的應(yīng)用流(flow)中自然地呈現(xiàn)產(chǎn)品。 在你的UI找到最好的位置來(lái)顯示你的應(yīng)用商店 UI。 在用戶可以使用它們的時(shí)候呈現(xiàn)產(chǎn)品---比如,當(dāng)用戶嘗試使用高級(jí)功能時(shí)讓用戶解鎖該功能。 特別關(guān)注用戶第一次使用你的應(yīng)用時(shí)的用戶體驗(yàn)。

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.組織產(chǎn)品,這樣探索就變得既簡(jiǎn)單又愉快。 如果你的應(yīng)用只有一點(diǎn)產(chǎn)品,你可以在一個(gè)屏幕上顯示所有產(chǎn)品;否則就把產(chǎn)品分組或分類讓用戶可以容易找到。 帶有大數(shù)量產(chǎn)品的應(yīng)用,比如,漫畫(huà)書(shū)或者有很多報(bào)道的雜志,制作一個(gè)可以讓用戶簡(jiǎn)單地發(fā)現(xiàn)它們想要購(gòu)買(mǎi)的新產(chǎn)品會(huì)特別有用。 給你的產(chǎn)品一個(gè)不同的名字和視覺(jué)效果,明確地區(qū)分它們--如有需要,包括明確地比較。

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、向用戶交流你的產(chǎn)品的價(jià)值。 用戶想要準(zhǔn)確地知道他們即將要買(mǎi)什么。 綜合應(yīng)用商店的信息,比如產(chǎn)品價(jià)格和描述,和服務(wù)器或應(yīng)用束中的附加數(shù)據(jù),比如,產(chǎn)品的圖片或 demos。 讓用戶在購(gòu)買(mǎi)之前以一種限制的方式體現(xiàn)產(chǎn)品。 舉個(gè)例子,有一個(gè)游戲,讓用戶選擇購(gòu)買(mǎi)新賽車(chē)(race cars)可以讓用戶用新車(chē)試跑一圈。 又或者,一個(gè)繪圖應(yīng)用,讓用戶購(gòu)買(mǎi)一個(gè)額外的筆刷可以讓用戶用新筆刷在一個(gè)小便簽上繪圖,讓它查看筆刷之間的區(qū)別。 這類的設(shè)計(jì)給用戶提供了一個(gè)體驗(yàn)產(chǎn)品的機(jī)會(huì)并說(shuō)服它們購(gòu)買(mǎi)。

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、使用應(yīng)用商店返回的語(yǔ)言環(huán)境(locale)和貨幣清楚地顯示價(jià)格。 確保能簡(jiǎn)單找到產(chǎn)品的價(jià)格并能簡(jiǎn)單地識(shí)別。 不要嘗試在你的 UI 中把價(jià)格轉(zhuǎn)換為一個(gè)不同的貨幣,即使用戶的語(yǔ)言環(huán)境和價(jià)格的語(yǔ)言環(huán)境不一樣。 想想看,一個(gè)在美國(guó)的用戶因?yàn)樗膯挝缓腿掌诟袷礁矚g英國(guó)的語(yǔ)言環(huán)境。 你的應(yīng)用根據(jù)英國(guó)的語(yǔ)言環(huán)境顯示它的 UI,但它任然需要用應(yīng)用商店指定的語(yǔ)言環(huán)境顯示產(chǎn)品信息。 為了嘗試匹配余下界面的英國(guó)語(yǔ)言環(huán)境,把價(jià)格轉(zhuǎn)換為英國(guó)英鎊是不正確的。 用戶在美國(guó)有一個(gè)應(yīng)用商店賬號(hào),它用美元支付,因此會(huì)給你的應(yīng)用提供一個(gè)以美元為單位的價(jià)格。還有,你得應(yīng)用將以美元為單元顯示價(jià)格。列表2-3 顯示了如何通過(guò)使用產(chǎn)品的語(yǔ)言環(huán)境信息來(lái)正確設(shè)置價(jià)格單位。

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.

當(dāng)用戶選擇好要購(gòu)買(mǎi)的產(chǎn)品后,你的應(yīng)用連接到應(yīng)用商店請(qǐng)求為該產(chǎn)品提供支付。

Suggested Testing Steps

四、建議測(cè)試步驟

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

測(cè)試代碼的每個(gè)部分來(lái)認(rèn)證你已經(jīng)正確地實(shí)現(xiàn)了該功能。

Sign In to the App Store with Your Test Account

1、用你的測(cè)試賬號(hào)登入應(yīng)用商店

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

在 iTunes Connect 里創(chuàng)建一個(gè)測(cè)試賬號(hào),請(qǐng)看 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.

在一個(gè) iOS 開(kāi)發(fā)設(shè)備中,在設(shè)置中退出應(yīng)用商店。然后從 Xcode 構(gòu)建和運(yùn)行你的應(yīng)用。

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.

在一個(gè) OS X 開(kāi)發(fā)設(shè)備中,退出 Mac 應(yīng)用商店。 然后在 Xcode 中構(gòu)建你的應(yīng)用,并從 Finder 中運(yùn)行它。

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.

使用你的應(yīng)該來(lái)完成一個(gè)內(nèi)置購(gòu)買(mǎi)。當(dāng)提示你登陸應(yīng)用商店時(shí),使用你的測(cè)試賬號(hào)。 注意提示框中出現(xiàn)的[Environment: Sandbox]文字提示你目前連接到測(cè)試環(huán)境。

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] 沒(méi)有出現(xiàn),則表示你使用的是產(chǎn)品環(huán)境。 確保你的應(yīng)用運(yùn)行在一個(gè)開(kāi)發(fā)簽署(development-signed)構(gòu)建。簽署的產(chǎn)品構(gòu)建使用產(chǎn)品環(huán)境。 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.

重要提示:不要用你的測(cè)試用戶賬號(hào)登陸產(chǎn)品環(huán)境,否則測(cè)試用戶賬號(hào)將無(wú)效不能再使用。

Test Fetching the List of Product Identifiers

  1. 測(cè)試獲取產(chǎn)品認(rèn)證碼列表

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.

如果你的產(chǎn)品認(rèn)證碼被整合進(jìn)應(yīng)用程序,在它們加載后,在代碼里設(shè)置一個(gè)斷點(diǎn),并認(rèn)證包含了預(yù)期產(chǎn)品識(shí)別碼列表的 NSArray 實(shí)例。

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.

如果你的產(chǎn)品識(shí)別碼是從服務(wù)器中獲取的,使用一個(gè)網(wǎng)絡(luò)瀏覽器如 Safari 或一個(gè)命令行工具如 curl 來(lái)手工獲取 JSON 文件,并認(rèn)證從服務(wù)器返回的數(shù)據(jù),該數(shù)據(jù)包含了預(yù)期的產(chǎn)品識(shí)別碼列表。 同時(shí)還要認(rèn)證你得服務(wù)器正確地實(shí)現(xiàn)了標(biāo)準(zhǔn) HTTP 緩存機(jī)制。

Test Handling of Invalid Product Identifiers

3、測(cè)試處理無(wú)效產(chǎn)品識(shí)別碼

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

在你的產(chǎn)品識(shí)別碼列表中故意包含進(jìn)一個(gè)無(wú)效識(shí)別碼。(確保在測(cè)試成功后刪除它)

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.

在一個(gè)產(chǎn)品構(gòu)建中,驗(yàn)證應(yīng)用程序顯示了其余的商店UI,用戶可以購(gòu)買(mǎi)其他的產(chǎn)品。 在一個(gè)開(kāi)發(fā)構(gòu)建中,驗(yàn)證應(yīng)用程序中引起你關(guān)注的問(wèn)題。

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

檢查控制臺(tái)日志并驗(yàn)證你可以正確地識(shí)別無(wú)效產(chǎn)品識(shí)別碼。

Test a Products Request

4、測(cè)試一個(gè)產(chǎn)品請(qǐng)求

Using the list of product identifiers that you tested, create and submit an instance ofSKProductsRequest . 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.

使用你測(cè)試好的產(chǎn)品識(shí)別碼列表,創(chuàng)建并遞交一個(gè)SKProductsRequest 實(shí)例。 在你的代碼中設(shè)置一個(gè)斷點(diǎn),檢查有效和無(wú)效的產(chǎn)品識(shí)別碼。 如果有無(wú)效產(chǎn)品識(shí)別碼,檢閱 iTunes Connect 中的產(chǎn)品并更正你的 JSON 文件或特性列表。