Wednesday, December 28, 2011

讓手機版面自動拉大到平板上(auto zoom instead of resize to fit tablet)

平板是全新的螢幕規格,
除非有特別去設計,
不然畫面會被resize到慘不忍睹

Android 3.2有提供一個全新的功能,
叫做「放大至全螢幕(zoom to fill screen)」。
這個功能是以480x320的手機解析度去模擬,
將畫面拉大到兼容平板畫面的大小,
唯一的缺點就是畫面會糊糊的

底下是我一隻APP「管理學決策模式II」的首頁,
這是800x480(手機版)解析度的正確畫面︰

再來看看平板上被resize後尷尬的畫面︰

如何強制讓手機畫面模擬到平板上呢?

在AndroidManifest.xml裡宣告︰

<supports-screens
android:xlargeScreens="true"
android:normalScreens="true"
android:smallScreens="true"
android:largestWidthLimitDp="320"
android:largeScreens="true"
android:resizeable="true"
android:anyDensity="true"/>

因為宣告了 android:largestWidthLimitDp="320"
程式就知道要以寬為320的解析度去呈現畫面。
底下是呈現效果︰

這篇文章獻給那些不想讓平板跑版、
又不想再去開發平板規格的懶人開發者。

註︰
1.開發環境需build在Android3.2以上
2.HTC Flyer上Android Market可以順利找到這隻APP, 這意謂著平板市場已經為你而開XD。

in-app billing關於使用者退款後,Google的心態。

很好奇萬一使用者退款了,
那我們程式這邊要不要把使用介面還原成未付費的樣子。

底下是in-app billing範例程式中,
PurchaseDatabase.java裡的其中一個函式updatePurchase(),
這個函式在您的APP收到使用者退款通知時,
會做資料庫購買記錄的修改。

底下是原始碼︰
 

   /**
     * Adds the given purchase information to the database and returns the total
     * number of times that the given product has been purchased.
     * @param orderId a string identifying the order
     * @param productId the product ID (sku)
     * @param purchaseState the purchase state of the product
     * @param purchaseTime the time the product was purchased, in milliseconds
     * since the epoch (Jan 1, 1970)
     * @param developerPayload the developer provided "payload" associated with
     *            the order
     * @return the number of times the given product has been purchased.
     */
    public synchronized int updatePurchase(String orderId, String productId,

        PurchaseState purchaseState, long purchaseTime, String developerPayload) {

        insertOrder(orderId, productId, purchaseState, purchaseTime, developerPayload);

        Cursor cursor = mDb.query(PURCHASE_HISTORY_TABLE_NAME, HISTORY_COLUMNS,
                HISTORY_PRODUCT_ID_COL + "=?", new String[] { productId }, null, null, null, null);

        if (cursor == null) {
            return 0;
        }

        int quantity = 0;

        try {

           // Count the number of times the product was purchased
            while (cursor.moveToNext()) {

                int stateIndex = cursor.getInt(2);
                PurchaseState state = PurchaseState.valueOf(stateIndex);

                // Note that a refunded purchase is treated as a purchase. Such
                // a friendly refund policy is nice for the user.
                if (state == PurchaseState.PURCHASED || state == PurchaseState.REFUNDED) {
                    quantity += 1;
                }

            }

            // Update the "purchased items" table
            updatePurchasedItem(productId, quantity);

        } finally {

            if (cursor != null) {
                cursor.close();
            }

        }

        return quantity;

    }
 

以上這段code説的、也做的夠清楚了,
範例程式收到使用者退款的IN_APP_NOTIFY後,
直接把Purchase Database的購買數量減1
卻沒有對程式畫面做任何處理。

範例裡留了這一段註解︰
// Note that a refunded purchase is treated as a purchase. Such a friendly refund policy is nice for the user.
即使使用者退款了,
我們仍以使用者是已購買的狀態來對待他,
這是一種友善政策。

Eclipse註解在Mac上變亂碼

有時候在Windows上的Eclipse開發完的案子,
註解在Mac上開起來卻變成亂碼,
主要原因是因為Windows的Eclipse預設文字編碼是Windwos系統編碼,
Mac不認識這種編碼造成的。

解決辦法就是將Windows上的編碼設成UTF-8,
這樣的話在Mac上就沒有問題了。

步驟
[現在你在windows的Eclipse環境底下]
1.先將一份Source Code複製至桌面
2.對著你的專案點擊滑鼠
2.選擇最下面的properties
3.出現以下的視窗後,將編碼設為UTF-8
4.此時會發現你原本的專案文字都變成亂碼,將桌面上的java頁面一頁一頁複製過來。
5.如此,Mac的開發員才會看到UTF-8編碼的Source Code。

簡言之,新的編碼格式是發生在Step3設定完後開始做編寫,才算術。

Saturday, December 24, 2011

[Android in-app billing第6篇(末)]In-app Billing Reference應用程式金流的相關API(中文翻譯)

這篇能獲得關於Android Market回應碼(response codes)和應用程式內部金流接口的詳細資訊。

原文連結︰In-app Billing Reference
翻譯︰小鰻
翻譯版本號︰v.1.1
如需轉載請註明出處「小鰻的Android學習筆記
讓我參與最直接的討論以及錯誤修正, 謝謝!

In this document

The following document provides technical reference information for the following:

 

Android Market Server Response Codes for In-app Billing針對應用程式金流機制,Android市集伺服器傳來的回應代碼

The following table lists all of the server response codes that are sent from Android Market to your application. Android Market sends these response codes asynchronously as response_code extras in the com.android.vending.billing.RESPONSE_CODE broadcast intent. Your application must handle all of these response codes.
底下的表格列出了我們APP發送給Android市集後,Android伺服器回傳過來的回應代碼。Android市集會以異步的方式,依response_code的extras在com.android.vending.billing.RESPONSE_CODE這個廣播意圖裡,回傳這些回應代碼。您的APP必須針對這些代碼做出相對應的處理。


Table 1. Summary of response codes returned by Android Market.
表1. 藉由Android市集回傳過來的回應碼摘要
Response Code回應代碼 Value值 Description描述
RESULT_OK 0 Indicates that the request was sent to the server successfully. When this code is returned in response to a CHECK_BILLING_SUPPORTED request, indicates that billing is supported.
此回應指出這次的購買請求已經成功的發送至Android市集伺服器了。當這個代碼在我們發出CHECK_BILLING_SUPPORTED請求時被回傳,就表示了此裝置的Android市集有支援iap機制。
RESULT_USER_CANCELED 1 Indicates that the user pressed the back button on the checkout page instead of buying the item.
此回應指出使用者在付費頁面下按了返回鍵而非購買商品。
RESULT_SERVICE_UNAVAILABLE 2 Indicates that the network connection is down.
此回應指出網路連線失效。
RESULT_BILLING_UNAVAILABLE 3 Indicates that in-app billing is not available because the API_VERSION that you specified is not recognized by the Android Market application or the user is ineligible for in-app billing (for example, the user resides in a country that prohibits in-app purchases).
此回應指出iap機制不被支援,主因是您指定的API_VERSION無法被Android市集軟體識別,或者使用者是無資格使用iap機制(舉例,使用者住在禁止使用iap機制的國家)
RESULT_ITEM_UNAVAILABLE 4 Indicates that Android Market cannot find the requested item in the application's product list. This can happen if the product ID is misspelled in your REQUEST_PURCHASE request or if an item is unpublished in the application's product list.
此回應指出Android市集無法找到此請求的應用程式內產品列表的商品。這可能是因為您在發送REQUEST_PURCHAS請求時,產品ID拚錯了,或者是在應用程式產品列表上的商品尚未被發佈。
RESULT_DEVELOPER_ERROR 5 Indicates that an application is trying to make an in-app billing request but the application has not declared the com.android.vending.BILLING permission in its manifest. Can also indicate that an application is not properly signed, or that you sent a malformed request, such as a request with missing Bundle keys or a request that uses an unrecognized request type.
此回應指出您的APP試圖發送iap請求,但是APP的AnddroidManifest.xml裡卻沒有宣告com.android.vending.BILLING權限。也可能是因為應用程式沒有正確的被簽署,或者您發送了一個非正確格式的請求,像是忘了傳Bundle的key值或者是使用了一個無法被識別的請求類型。
RESULT_ERROR 6 Indicates an unexpected server error. For example, this error is triggered if you try to purchase an item from yourself, which is not allowed by Google Checkout.
此回應指出Android市集傳來了一個無法預期的伺服器錯誤。舉例來說,這個錯誤是出自您居然想要購買您自己在販售的商品,而這個商品卻沒有被Google Checkout允許販售。

 

In-app Billing Service Interface應用程式金流服務的接口

The following section describes the interface for Android Market's in-app billing service. The interface is defined in the IMarketBillingService.aidl file, which is included with the in-app billing sample application.
底下的段落將描述Android市集iap機制服務的接口。這個接口被定義在IMarketBillingService.aidl檔裡,這個檔被包在iap範例程式裡。
The interface consists of a single request method sendBillingRequest(). This method takes a single Bundle parameter. The Bundle parameter includes several key-value pairs, which are summarized in table 2.
這個接口是由一個叫sendBillingRequest()的請求函式組成的。這個函式有一個Bundle參數,該Bundle參數包含數對key-value,這些key-value會在表2做摘要說明。

Table 2. Description of Bundle keys passed in a sendBillingRequest() request.
表2. 描述在sendBillingRequest()請求裡,傳送Bundle給市集的key有哪些
Key Type型態 Possible Values
有效值
Required?
需要?
Description描述
BILLING_REQUEST String CHECK_BILLING_SUPPORTED, REQUEST_PURCHASE, GET_PURCHASE_INFORMATION, CONFIRM_NOTIFICATIONS, or RESTORE_TRANSACTIONS Yes The type of billing request you are making with the sendBillingRequest() request. The possible values are discussed more below this table.
這些是您在發送sendBillingRequest()請求時回應您的的金流請求類型值。這些有效值會在這個表格的下面被討論。
API_VERSION int 1 Yes The version of Android Market's in-app billing service you are using. The current version is 1.
告知您正在使用的iap機制服務的Android市集版號。正確值為1
PACKAGE_NAME String A valid package name.有效的套件名稱 Yes The name of the application that is making the request.
請求購買商品的應用程式名稱。
ITEM_ID String Any valid product identifier.有效的產品識別碼 Required for REQUEST_PURCHASE requests.
當發出REQUEST_PURCHASE請求時會需要
The product ID of the item you are making a billing request for. Every in-app item that you sell using Android Market's in-app billing service must have a unique product ID, which you specify on the Android Market publisher site.
您正在請求購買的產品ID。每次您所販售Android市集iap服務的產品ID都必須是唯一。這些ID被您在Android市集發佈網站指定。
NONCE long Any valid long value.任何有效的long值 Required for GET_PURCHASE_INFORMATION and RESTORE_TRANSACTIONS requests.
當發出GET_PURCHASE_INFORMATION和RESTORE_TRANSACTIONS請求時會需要。
A number used once. Your application must generate and send a nonce with each GET_PURCHASE_INFORMATION and RESTORE_TRANSACTIONS request. The nonce is returned with the PURCHASE_STATE_CHANGED broadcast intent, so you can use this value to verify the integrity of transaction responses form Android Market.
僅用一次的數值。您的APP必須在每次發出GET_PURCHASE_INFORMATIONhdr
RESTORE_TRANSACTIONS請求時,產生並發生出一個隨機數。這組隨機數會在Android市集發出PURCHASE_STATE_CHANGED這個廣播意圖時回傳給您。因此您可以用這個值來驗証從Android市集傳來的完整交易回應。
NOTIFY_IDS Array of long values Any valid array of long values有效的long型態陣列值 Required for GET_PURCHASE_INFORMATION and CONFIRM_NOTIFICATIONS requests.
當發出GET_PURCHASE_INFORMATION和CONFIRM_NOTIFICATIONS請求時會需要。
An array of notification identifiers. A notification ID is sent to your application in an IN_APP_NOTIFY broadcast intent every time a purchase changes state. You use the notification to retrieve the details of the purchase state change.
這是一個訊息通知識別碼的陣列值。訊息通知ID在每次購買狀態遭改變時,Android市集發送IN_APP_NOTIFY廣播意圖時夾帶並傳送給您。
DEVELOPER_PAYLOAD
開發者的酬載 
(譯者註︰在資料安全領域裡,往往在資料的傳輸過程會加入一些特定值,來確認每一次的傳輸皆為安全的。payload就是一個為了資料安全而存在的值)
String Any valid String less than 256 characters long.有效值在256個字元內 No A developer-specified string that can be specified when you make a REQUEST_PURCHASE request. This field is returned in the JSON string that contains transaction information for an order. You can use this key to send supplemental information with an order. For example, you can use this key to send index keys with an order, which is useful if you are using a database to store purchase information. We recommend that you do not use this key to send data or content.
這是一個開發者自訂的字串值。每當您發出REQUEST_PURCHASE請求時可以拿這組字串值做特殊的標註。這個字串會在市集回傳包含訂單的交易資訊JSON字串時被夾帶並回傳回來。您可以使用這個key來發送訂單補充說明的資訊。舉例,您可以使用這個key來發送訂單的索引key,這在假設您正使用資料庫來儲存購買資訊時會很有用。我們建議您不要使用這個key值來發送資料或內容。

The BILLING_REQUEST key can have the following values:
BILLING_REQUEST的key值可以帶下列這些︰
  • CHECK_BILLING_SUPPORTED This request verifies that the Android Market application supports in-app billing. You usually send this request when your application first starts up. This request is useful if you want to enable or disable certain UI features that are relevant only to in-app billing.
  • CHECK_BILLING_SUPPORTED 這樣請求是拿來做Android市集軟體是否支援iap機制的驗証用的。通常在您的APP第1次啟動時,會發出這個請求。這個請求在您想要啟動或取消特定的使用介面的功能(這些功能是提供給付費功能用的)時,是很有用的。
  • REQUEST_PURCHASE This request sends a purchase message to the Android Market application and is the foundation of in-app billing. You send this request when a user indicates that he or she wants to purchase an item in your application. Android Market then handles the financial transaction by displaying the checkout user interface.
  • REQUEST_PURCHASE 這個請求是iap機制的基礎,會發送購買訊息至Android市集軟體。當使用者想要購買應用程式內商品時,您就可以發送此請求。Android市集會呈現付費使用介面給使用者並處理接著會處理金融交易。
  • GET_PURCHASE_INFORMATION This request retrieves the details of a purchase state change. A purchase state change can occur when a purchase request is billed successfully or when a user cancels a transaction during checkout. It can also occur when a previous purchase is refunded. Android Market notifies your application when a purchase changes state, so you only need to send this request when there is transaction information to retrieve.
  • GET_PURCHASE_INFORMATION這個請求會去接收購買狀態遭改變的詳細資訊。當購買請求付費成功或當使用者在付費途中取消了交易,都會發生購買狀態遭改變這個事件。當然,這也可能是使用者退費了之前的商品購買。Android市集一旦遇到商品狀態遭改變時,就會通知您的APP,因此,這個請求只要在Android市集要求您接收交易資訊時再發出即可。
  • CONFIRM_NOTIFICATIONS This request acknowledges that your application received the details of a purchase state change. That is, this message confirms that you sent a GET_PURCHASE_INFORMATION request for a given notification and that you received the purchase information for the notification.
  • CONFIRM_NOTIFICATIONS 這個請求目的是向Android市集承認您已經收到購買狀態遭改變的詳細資訊。因此,這個訊息也可以說是向Android市集再次確認您之前發送過GET_PURCHASE_INFORMATION出去,您已經接收到了購買資訊的通知了。
  • RESTORE_TRANSACTIONS This request retrieves a user's transaction status for managed purchases (see Choosing a Purchase Type for more information). You should send this message only when you need to retrieve a user's transaction status, which is usually only when your application is reinstalled or installed for the first time on a device.
  • RESTORE_TRANSACTIONS 這個請求接收了使用者被管理的購買商品的交易狀態(見Choosing a Purchase Type查看更多資訊)。若要發送此請求,應該只會在當您需要接收使用者的交易狀態,由其是您的APP被再次安裝或者在裝置上第1次安裝時。
Every in-app billing request generates a synchronous response. The response is a Bundle and can include one or more of the following keys:
每次iap請求都會產生從Android市集來的同步回應。這些回應都以Bundle傳送, 裡面也包含了一至多組的key值,key值如下︰
  • RESPONSE_CODE This key provides status information and error information about a request.
  • RESPONSE_CODE 這個key值提供關於請求的狀態資訊和錯誤資訊。
  • PURCHASE_INTENT This key provides a PendingIntent, which you use to launch the checkout activity.
  • PURCHASE_INTENT 這個請求提供了一個PendingIntent,它讓您可以啟動付費的Activity。
  • REQUEST_ID This key provides you with a request identifier, which you can use to match asynchronous responses with requests.
  • REQUEST_ID 這個key值提供您請求的識別碼,可以用這個碼來替傳來的異步回應做比對是否相符。
Some of these keys are not relevant to certain types of requests. Table 3 shows which keys are returned for each request type.
這裡的有些key值跟某些特定類型的請求並不相關。表3顯示了每個請求類型各會傳回哪些key值。


Table 3. Description of Bundle keys that are returned with each in-app billing request type.
表3. 每個iap機制請求類型各回傳的Bundle key值描述
Request Type請求類型 Keys Returned傳回的key值 Possible Response Codes可能傳回的回應碼
CHECK_BILLING_SUPPORTED
檢查裝置是否支援iap
RESPONSE_CODE RESULT_OK, RESULT_BILLING_UNAVAILABLE, RESULT_ERROR, RESULT_DEVELOPER_ERROR
REQUEST_PURCHASE
請求購買
RESPONSE_CODE, PURCHASE_INTENT, REQUEST_ID RESULT_OK, RESULT_ERROR, RESULT_DEVELOPER_ERROR
GET_PURCHASE_INFORMATION
取得購買資訊
RESPONSE_CODE, REQUEST_ID RESULT_OK, RESULT_ERROR, RESULT_DEVELOPER_ERROR
CONFIRM_NOTIFICATIONS
確認傳來的通知訊息
RESPONSE_CODE, REQUEST_ID RESULT_OK, RESULT_ERROR, RESULT_DEVELOPER_ERROR
RESTORE_TRANSACTIONS
還原交易狀態至APP裡
RESPONSE_CODE, REQUEST_ID RESULT_OK, RESULT_ERROR, RESULT_DEVELOPER_ERROR

 

In-app Billing Broadcast Intents應用程式金流傳來的廣播意圖

The following section describes the in-app billing broadcast intents that are sent by the Android Market application. These broadcast intents inform your application about in-app billing actions that have occurred. Your application must implement a BroadcastReceiver to receive these broadcast intents, such as the BillingReceiver that's shown in the in-app billing sample application.
底下的段落會描述由Android市集軟體傳來的iap機制廣播意圖。這些廣播意圖會通知您的APP關於iap機制的動作發生了。您的APP必須去實作一個廣播接收機制(BroadcastReceiver)去接收這些傳來的廣播意圖,像是iap範例程式裡的BillingReceiver就是這樣的一個元件。

com.android.vending.billing.RESPONSE_CODE

This broadcast intent contains an Android Market response code, and is sent after you make an in-app billing request. A server response code can indicate that a billing request was successfully sent to Android Market or it can indicate that some error occurred during a billing request. This intent is not used to report any purchase state changes (such as refund or purchase information). For more information about the response codes that are sent with this response, see Android Market Response Codes for In-app Billing. The sample application assigns this broadcast intent to a constant named ACTION_RESPONSE_CODE.
這個廣播意圖包含了從Android市集而來的回應碼,是在您發送了iap金流請求後傳來的。回應碼可以表示金流請求是否成功的傳至Android市集。這個意圖不是用來報告任何購買狀態遭改變(像是退費或購買資訊)。更多發送請求得到此回應的資訊,請見Android Market Response Codes for In-app Billing這一篇。範例程式裡將這個廣播意圖指派到一個叫ACTION_RESPONSE_CODE的實體。
Extras其它傳來的值
  • request_id—a long representing a request ID. A request ID identifies a specific billing request and is returned by Android Market at the time a request is made.
  • request_id - 代表這次請求ID的一個long值。請求的ID是拿來識別特定金流請求,而且是由Android市集在請求的同一時間回傳過來的。
  • response_code—an int representing the Android Market server response code.
  • response_code - 代表Android市集伺服器的一個int值回應碼。

com.android.vending.billing.IN_APP_NOTIFY

This response indicates that a purchase has changed state, which means a purchase succeeded, was canceled, or was refunded. This response contains one or more notification IDs. Each notification ID corresponds to a specific server-side message, and each messages contains information about one or more transactions. After your application receives an IN_APP_NOTIFY broadcast intent, you send a GET_PURCHASE_INFORMATION request with the notification IDs to retrieve the message details. The sample application assigns this broadcast intent to a constant named ACTION_NOTIFY.
這個回應指出購買狀態遭到改變了,也就是說購買成功了,也或者取消、甚至退費了。這個回應包含了一至多個訊息通知IDs。每一個訊息通知ID都與特定的伺服端訊息相對應,每個訊信也包含了關於一或多個交易的資訊。當您的APP接收到了IN_APP_NOTIFY這個廣播意圖後,您就要發送含這個訊息通知ID的GET_PURCHASE_INFORMATION請求出去,接收詳細的交易訊息。範例程式將這個廣播意圖指派至一個名叫ACTION_NOTIFY的實體。
Extras其它傳來的值
  • notification_id—a String representing the notification ID for a given purchase state change. Android Market notifies you when there is a purchase state change and the notification includes a unique notification ID. To get the details of the purchase state change, you send the notification ID with the GET_PURCHASE_INFORMATION request.
  • notification_id - 代表購買狀態遭改變的訊息通知ID,是一個String值。Android市集會在當購買狀態遭到改變時,傳送一個唯一性的訊息通知ID給您。如果想要取得購買狀態改變的詳細資訊,就要發送一個含訊息通知ID的GET_PURCHASE_INFORMATION請求至Android市集。

com.android.vending.billing.PURCHASE_STATE_CHANGED

This broadcast intent contains detailed information about one or more transactions. The transaction information is contained in a JSON string. The JSON string is signed and the signature is sent to your application along with the JSON string (unencrypted). To help ensure the security of your in-app billing messages, your application can verify the signature of this JSON string. The sample application assigns this broadcast intent to a constant named ACTION_PURCHASE_STATE_CHANGED.
這個廣播意圖夾帶了一或多個交易的詳細資訊。 交易的詳細資訊是由JSON字串傳來的,此外,這個JSON不僅被簽署過,還順便傳來一個數位簽章(未加密的狀態)。為了幫助您確認您iap機制訊息的安全,您的APP可以驗証這個JSON字串傳來的數位簽章。範例程式中將PURCHASE_STATE_CHANGE這個廣播意圖指派到一個叫ACTION_PURCHASE_STATE
_CHANGED的實體。
Extras其它傳來的值
  • inapp_signed_data—a String representing the signed JSON string.
  • inapp_signed_data - 一個簽署過的JSON字串。
  • inapp_signature—a String representing the signature.
  • inapp_signature - 一個數位簽章字串。
Note: Your application should map the broadcast intents and extras to constants that are unique to your application. See the Consts.java file in the sample application to see how this is done.
The fields in the JSON string are described in the following table (see table 4)
註︰您應該在您的APP裡詳細的計劃每一個廣播意圖和其它傳來的值的實體都具有唯一性。 請見範例程式裡Consts.java檔是如何做的。
JSON字串的值都描述至下列的表格中(見表4)

Table 4. Description of JSON fields that are returned with a PURCHASE_STATE_CHANGED intent.
表4. 藉由PURCHASE_STATE_CHANGE意圖傳來的JSON值的描述
Field值 Description描述
nonce
隨機數
A number used once. Your application generates the nonce and sends it with the GET_PURCHASE_INFORMATION request. Android Market sends the nonce back as part of the JSON string so you can verify the integrity of the message.
僅用一次的一個數值。當要發送GET_PURCHASE_INFORMATION請求時,您的APP要產生一組隨機數一起發送。Android市集會再將這個隨機數塞進JSON字串當中,傳回給您。因此您可以用這個方法來驗証Android市集傳來的訊息的完整性。
notificationId
訊息通知id
A unique identifier that is sent with an IN_APP_NOTIFY broadcast intent. Each notificationId corresponds to a specify message that is waiting to be retrieved on the Android Market server. Your application sends back the notificationId with the GET_PURCHASE_INFORMATION message so Android Market can determine which messages you are retrieving.
這是從IN_APP_NOTIFY廣播意圖一起傳來的唯一性識別碼(unique identifier)。每次Android市集發出IN_APP_NOTIFY時,市集伺服器自己會留住這組識別碼,因此當您的APP之後透過GET_PURCHASE_INFORMATION訊息傳送這組識別碼回去時,Android市集就能清楚的知道您剛才接收的是哪一個訊息。
orderId
訂單id
A unique order identifier for the transaction. This corresponds to the Google Checkout Order ID.
這是這次交易的唯一性訂單識別碼(unique order identifier) ,這個識別碼會和Google Checkout的訂單編號ID相符。
packageName
套件名稱
The application package from which the purchase originated.
APP套件的購買起源(譯者註︰不確定是否正確)
productId
產品id
The item's product identifier. Every item has a product ID, which you must specify in the application's product list on the Android Market publisher site.
商品的產品識別碼。每個商品都有產品ID,您必須在Android市集發佈網站裡的應用程式產品列表裡指定這些產品ID。
purchaseTime
購買時間
The time the product was purchased, in milliseconds since the epoch (Jan 1, 1970).
購買商品的時間。 從32位元的起源時間算起(1970/07/01)的毫秒時間。
(譯者註︰可以到此網站換算現在時間。)
purchaseState
購買狀態
The purchase state of the order. Possible values are 0 (purchased), 1 (canceled), or 2 (refunded).
訂單的購買狀態。有效值為0(已購買)、1(購買中途取消)、2(退費)。
developerPayload
開發者的酬載
A developer-specified string that contains supplemental information about an order. You can specify a value for this field when you make a REQUEST_PURCHASE request.
開發者指定的一組字串,用來補充關於訂單的資訊。當您要發出REQUEST_PURCHASE請求時,可以指定這個值。

相關文章︰
1.[Android in-app billing前言]In-app Billing應用程式內部付費機制(中文翻譯)
2.[Android in-app billing第1篇]In-app Billing Overview應用程式內部付費機制概述(中文翻譯)
3.[Android in-app billing第2篇]Implementing In-app Billing實作應用程式內部金流機制(中文翻譯)
4.[Android in-app billing第3篇]Security and Design安全與設計(中文翻譯)
5.[Android in-app billing第4篇]Testing In-app Billing測試應用程式內金流機制(中文翻譯)
6.[Android in-app billing第5篇]Administering In-app Billing應用程式內金流機制的管理(中文翻譯)
7.[Android in-app billing第6篇(末)]In-app Billing Reference應用程式金流的相關API(中文翻譯)

Friday, December 23, 2011

[Android in-app billing第5篇]Administering In-app Billing應用程式內金流機制的管理(中文翻譯)

學習如何設定你的產品列表、註冊測試帳戶和處理退款的問題。

原文連結︰Administering In-app Billing
翻譯︰小鰻
翻譯版本號︰v.1.0
如需轉載請註明出處「小鰻的Android學習筆記
讓我參與最直接的討論以及錯誤修正, 謝謝!

In this document

In-app billing frees you from processing financial transactions, but you still need to perform a few administrative tasks, including setting up and maintaining your product list on the publisher site, registering test accounts, and handling refunds when necessary.
You must have an Android Market publisher account to register test accounts. And you must have a Google Checkout merchant account to create a product list and issue refunds to your users. If you already have a publisher account on Android Market, you can use your existing account. You do not need to register for a new account to support in-app billing. If you do not have a publisher account, you can register as an Android Market developer and set up a publisher account at the Android Market publisher site. If you do not have a Google Checkout merchant account, you can register for one at the Google Checkout site.
雖然説應用程式內金流機制(以下簡稱iap機制)讓你金融交易的流程更佳的彈性了,但是您仍有一些管理的工作要做,包含設定和管理您在發佈網站商的商品、註冊測試帳戶以及當流程需要時,能夠處理退費事件發生該有的對應。您必須在Android發佈網站註冊一組測試帳戶,而且您必須擁有Google Checkout merchant帳戶來建立產品列表以及處理來至於您APP的使用用戶所請求的退費相關問題。如果您已經擁有Android市集的發佈帳號了,使用既有的帳號即可,就不需要再去申請一組為了要支援iap機制而申請的新帳號。如果您沒有發佈帳號,那就去申請一組吧。如果您沒有Google Checkout merchant帳號,您也可以註冊一組Google Checkout網站的帳號。

Creating a Product List建立產品列表

The Android Market publisher site provides a product list for each of your published applications. You can sell an item using Android Market's in-app billing feature only if the item is listed on an application's product list. Each application has its own product list; you cannot sell items that are listed in another application's product list.
You can access an application's product list by clicking the In-App Products link that appears under each of the applications that are listed for your publisher account (see figure 1). The In-App Products link appears only if you have a Google Checkout merchant account and an application's manifest includes the com.android.vending.BILLING permission.
Android市集發佈網站提供您每一個發佈的APP的產品列表,您要銷售的應用程式內商品僅能來至於這張列表上的商品。每一個應用程都擁有自已的列表清單,您無法銷售別隻APP裡的產品列表商品至另一隻APP裡。
存取應用程式產品列表的方式,就是點擊每一個軟體下方的In-App Products連結(見圖1)。In-App Products連結會在如果您擁有Google Checkout merchant帳戶,並且APP裡的Androidmanifest.xml檔有宣告com.android.vending.BILLING權限時,才會出現。

Figure 1. You can access an application's product list by clicking the In-App Products link.
圖1. 您可以透過點擊In-App Products連結的方式來存取應用程式產品列表。
A product list contains information about the items you are selling, such as a product id, product description, and price (see figure 2). The product list stores only metadata about the items you are selling in your application. It does not store any digital content. You are responsible for storing and delivering the digital content that you sell in your applications.
產品列表列出了您目前販賣的商品資訊,像是產品的id、產品描述或價格(見圖2)。產品列表僅會儲存關於您在您APP裡賣的商品的詮釋資料(metadata)。並不會儲任何的數位化內容。儲存和傳遞您售於APP內的數位內容是您的責任。

Figure 2. An application's product list.
圖2. 這是一隻APP裡的產品列表

You can create a product list for any published application or any draft application that's been uploaded and saved to the Android Market site. However, you must have a Google Checkout merchant account and the application's manifest must include the com.android.vending.BILLING permission. If an application's manifest does not include this permission, you will be able to edit existing items in the product list but you will not be able to add new items to the list. For more information about this permission, see Updating Your Application's Manifest.
您可以替任何已發佈出去或上傳並儲存至Android市集網站的草稿型APP建立個別的產品列表。然而,您必須擁有Google Checkout merchant帳戶,APP裡的Androidmanifest.xml檔也必須包含com.android.vending.BILLING的權限宣告。如果沒有做此宣告,您還是可以編輯之前已存在過的產品列表,但您也因而無法再新增商品了。更多關於權限的資訊,請參見Updating Your Application's Manifest

In addition, an application package can have only one product list. If you create a product list for an application, and you use the multiple APK feature to distribute more than one APK for that application, the product list applies to all APK versions that are associated with the application listing. You cannot create individual product lists for each APK if you are using the multiple APK feature.
附帶一提,一個APP套件僅能擁有一個產品列表。如果您替一個APP建立了產品列表,然後您使用一款應用程式多種版本功能的方式來發佈1隻APP,產品列表接受的是來自各種版本的所有連結。您無法替各個版本的APK建立特定的產品列表。

You can add items to a product list two ways: you can add items one at a time by using the In-app Products UI (see figure 3), or you can add a batch of items by importing the items from a comma-separated values (CSV) file (see figure 2). Adding items one at a time is useful if your application has only a few in-app items or you are adding only a few items to a product list for testing purposes. The CSV file method is useful if your application has a large number of in-app items.
您可以使用2種方式來新增商品至產品列表︰使用同時間單一產品上架的iap產品使用介面(見圖3),或者您可以CSV檔匯入(見圖2)。如果您的APP只有幾個應用程式內商品要銷售或拿來做測試,前者的方式是很有用的。CSV檔的方式則是在如果有大量的應用程式內商品要銷售時有用。

Adding items one at a time to a product list同時間新增一件商品至產品列表

To add an item to a product list using the In-app Products UI, follow these steps:
如果要使用應用程式商品使用介面來新增商品列表,請跟著底下的步驟︰
  1. Log in to your publisher account.
  2. 登入您的發佈帳戶
  3. In the All Android Market listings panel, under the application name, click In-app Products.
  4. 在All Android Market listings區塊裡,APP名稱底下,點擊In-app Products.
  5. On the In-app Products List page, click Add in-app product.
  6. 在In-app Products列表頁面底下,點擊Add in-app product.
  7. On the Create New In-app Product page (see figure 3), provide details about the item you are selling and then click Save or Publish.
  8. 在建立新的應用程式商品頁面裡(見圖3),提供了您正在售的商品的商品資訊以及儲存/發佈按鈕。

Figure 3. The Create New In-app Product page lets you add items to an application's product list. 
圖3. 這是讓您可以新增應用程式產品列表的頁面
You must enter the following information for each item in a product list:
產品列表裡的每件商品,您都必須輸入下列的資訊︰
  • In-app Product ID Product IDs are unique across an application's namespace. A product ID must start with a lowercase letter or a number, and must be composed using only lowercase letters (a-z), numbers (0-9), underlines (_), and dots (.). The product ID "android.test" is reserved, as are all product IDs that start with "android.test." In addition, you cannot modify an item's product ID after it is created, and you cannot reuse a product ID.
  • In-app Product ID 產品IDs是以唯一性的方式跨越應用程式命名空間。產品ID必須啟始字元必須為小寫或數字,而且組成的字串也都只能有小寫(a-z)、數字(0-9)、下底線(_)和小數點(.)。以"android.test"開頭的產品ID命名被保留,任何以android.test開頭的命名方式皆不可用。附帶一提,當您在建立產品ID後,是無法修改的,而且您也無法重覆使用同一組產品ID。
  • Purchase Type The purchase type can be Managed per user account or Unmanaged. You can never change an item's purchase type after you set it. For more information, see Choosing a purchase type later in this document.
  • Purchase Type 購買的商品型態被區分成「受管理(依帳號)」和「不受管理」兩類。當您設定完商品種類後,就無法改變了。更多資訊,請參閱接下來Choosing a purchase type這個章節。
  • Publishing State An item's publishing state can be Published or Unpublished . To be visible to a user during checkout, an item's publishing state must be set to Published and the item's application must be published on Android Market.
    Note: This is not true for test accounts. An item is visible to a test account if the application is not published and the item is published. See Testing In-app Billing for more information.
    Publishing State 商品發佈狀態區分為已發佈或未發佈2種型態。如果要讓商品在付費期間能夠被看見,商品狀態就應該設為已發佈,而且擁有該商品的APP也應該是以「已發佈」的狀態存放在Android市集上。
    註︰如果是測試帳戶就不在此限。因為當您在測試時,測試帳戶允許你以不發佈APP、而內部商品為已發佈的狀態來進行。可以查看Testing In-app Billing得到更多資訊。
  • Language The language setting determines which languages are used to display the item title and item description during checkout. A product list inherits its default language from the parent application. You can add more languages by clicking add language. You can also choose to have the title and description automatically translated from the default language by selecting the Fill fields with auto translation checkbox (see figure 4). If you do not use the auto translation feature, you must provide the translated versions of the title and description.
  • 語系 語系的設定決定了在付費期間,哪種語言會顯示哪種的商品標題或商品描述。產品列表的語系呈現方式是從您APP的語系設定傳過來的。您可以透過點擊新增語系來新增更多的應用商品產品的語言。您也可以透過點擊自動翻譯並填入的選項來讓語系自動判別並呈現(見圖4)。如果您沒有使用自動翻譯這個功能,您就必須提供商品標題和商品描述的翻譯版本進來。
  • Title The title is a short descriptor for the item. For example, "Sleeping potion." Titles must be unique across an application's namespace. Every item must have a title. The title is visible to users during checkout. For optimum appearance, titles should be no longer than 25 characters; however, titles can be up to 55 characters in length.
  • 標題 標題是商品的短描述。舉例︰「睡眠藥劑」。標題在您APP的命名裡必須是唯一性質、不可重覆的。每個商品都需要有標題,這個標題在使用者付費的期間是會被看到的。為了更清楚的表達商品,標題最好不要超過25個字元。然而;標題的上限會在55個字元內。
  • Description The description is a long descriptor for the item. For example, "Instantly puts creatures to sleep. Does not work on angry elves." Every item must have a description. The description is visible to users during checkout. Descriptions can be up to 80 characters in length.  
  • 描述 描述是用來介紹商品的長字串。舉例︰「此物品會馬上讓動物睡著,但無法讓愛生氣的小精靈起作用。」。每個商品都必須有個描述,這個描述在使用者付費期間,也是會被看到的。最長是80個字元。
  • Price You must provide a default price in your home currency. You can also provide prices in other currencies, but you can do this only if a currency's corresponding country is listed as a target country for your application. You can specify target countries on the Edit Application page in the Android Market developer console.
    To specify prices in other currencies, you can manually enter the price for each currency or you can click Auto Fill and let Android Market do a one-time conversion from your home currency to the currencies you are targeting (see figure 4).
  • 價格 您必須用您所在地區的匯率來提供商品價格。您也可以以其它的匯率來計算您的商品價格,但這麼做只會發生在如果那個國家是您APP的主要市場。您可以在Android市集的開發人員控制臺的編輯APP頁面裡去指定販售的目標國家。 如果要指定成其它匯率,您可以依手動的方式輸入每個國家匯率而訂的價格或者也可以使用點擊自動填入的方式,讓Android市集從您的國家匯率自動轉至它國的匯率(見圖4)。

Figure 4. Specifying additional currencies and additional languages for the item title and description. 
圖4. 替每件商品的標題和描述指定其它的匯率和其它的語系 。

For more information about product IDs and product lists, see Creating In-App Product IDs. For more information about pricing, see In-App Billing Pricing.
Note: Be sure to plan your product ID namespace. You cannot reuse or modify product IDs after you save them.
更多關於產品IDs和產品列表的資訊,請參閱Creating In-App Product IDs。如果想知道價格的資訊,則參閱 In-App Billing Pricing這篇。
註︰請有計劃的規劃您的產品ID命名。因為一旦商品被儲存,產品ID就無法被更改了。

Adding a batch of items to a product list增加批量商品至產品列表

To add a batch of items to a product list using a CSV file, you first need to create your CSV file. The data values that you specify in the CSV file represent the same data values you specify manually through the In-app Products UI (see Adding items one at a time to a product list). The CSV file uses commas (,) and semi-colons (;) to separate data values. Commas are used to separate primary data values, and semi-colons are used to separate subvalues. For example, the syntax for the CSV file is as follows:
使用CSV檔來新增批量商品,首先您必須建立您的CSV檔。CSV裡的資料呈現方式就如同您在產品使用介面以手動的方式新增商品一樣。 (見 Adding items one at a time to a product list)。CSV檔使用逗號(,)和分號(;)來分隔資料。逗號用來分隔主要資料的值,而分號用來分隔次資料。舉例,一個CSV檔裡的語法應該像下面這樣子︰
"product_id","publish_state","purchase_type","autotranslate ","locale; title; description","autofill","country; price

Descriptions and usage details are provided below.
底下是描述和使用方式︰
  • product_id This is equivalent to the In-app Product ID setting in the In-app Products UI. If you specify a product_id that already exists in a product list, and you choose to overwrite the product list while importing the CSV file, the data for the existing item is overwritten with the values specified in the CSV file. The overwrite feature does not delete items that are on a product list but not present in the CSV file.
  • product_id 這個值如同iap商品使用介面裡的Product ID設定值。如果產品列表裡已經有這筆product_id,而且當您在匯入CSV檔時想覆寫商品使用介面裡的Product_ID的話,這個值就會被您CSV裡所指定的新資料取代。覆寫的狀況不會發生在CSV檔裡沒有重覆的product_id的情形下。
  • publish_state This is equivalent to the Publishing State setting in the In-app Products UI. Can be published or unpublished.
  • publish_state 這個值等同於iap產品使用介面裡的發佈狀態設定,一樣可以設成已發佈或未發佈的狀態。
  • purchase_type This is equivalent to the Purchase Type setting in the In-app Products UI. Can be managed_by_android, which is equivalent to Managed per user account in the In-app Products UI, or managed_by_publisher, which is equivalent to Unmanaged in the In-app Products UI.
  • purchase_type 這個值等同於iap產品使用介面裡的購買狀態設定值。會依使用帳戶做管理的值是managed_by_android,不受管理的值是managed_by_publisher。
  • autotranslate This is equivalent to selecting the Fill fields with auto translation checkbox in the In-app Products UI. Can be true or false.
  • autotranslate 這個值等同於在iap商品使用介面裡選擇了自動翻譯並填入選項的功能,可以是true,也可以是false。
  • locale This is equivalent to the Language setting in the In-app Products UI. You must have an entry for the default locale. The default locale must be the first entry in the list of locales, and it must include a title and description. If you want to provide translated versions of the title and description in addition to the default, you must use the following syntax rules:
  • 地區 這個值如同iap產品使用介面的語系設定。您必須設一個預設的地區,而且預設的地區也要設在第1位,且包含標題和描述。如果您想要將自動翻譯設為預設值,您就必須使用底下的語法規則︰
    If autotranslate is true, you must specify the default locale, default title, default description, and other locales using the following format:
    如果自動翻譯設成true,您必須指定預設的地區、預設的標題、預設的描述以及其它地區的使用格式︰
    "true,"default_locale; default_locale_title; default_locale_description; locale_2; locale_3, ..."
    If autotranslate is false, you must specify the default locale, default title, and default description as well as the translated titles and descriptions using the following format:
    如果自動翻譯設成false,您必須指定預設的地區、預設的標題和預設的描述,以及翻譯過後的標題、描述,並使用底下格式︰
    "false,"default_locale; default_locale_title; default_locale_description; locale_2; locale_2_title; local_2_description; locale_3; locale_3_title; locale_3_description; ..."
    See table 1 for a list of the language codes you can use with the locale field. 請見表1列出的您可以使用的語系代碼和語系值
  • title This is equivalent to the Title setting in the In-app Products UI. If the title contains a semicolon, it must be escaped with a backslash (for example, "\;"). A backslash should also be escaped with a backslash (for example, "\\">.
  • 標題 這個值等同語iap產品使用介面裡的標題設定。如果標題包含分號,就必須加上反斜線加以區隔(如"\;")。如果標題含反斜線,也一樣要加上反斜線(如︰"\\")。
  • description This is equivalent to the Description in the In-app Products UI. If the description contains a semicolon, it must be escaped with a backslash (for example, "\;"). A backslash should also be escaped with a backslash (for example, "\\">.
  • 描述 這個值等同語iap產品使用介面的描述值。如果描述值包含分號,就必須加以反斜線加以區隔(如︰"\;")。如果含的是反斜線,就再加上反斜線來區隔。(如︰"\\")。
  • autofill This is equivalent to clicking Auto Fill in the In-app Products UI. Can be true or false. The syntax for specifying the country and price varies depending on which autofill setting you use.
  • autofill 這個值等同於iap產品使用介面裡點擊自動填入。可以設為true或false。若要指定出不同的國家或價格完全取決於您的是否設定autofill。
    If autofill is set to true, you need to specify only the default price in your home currency and you must use this syntax:
    如果autofill設為true,您僅需指定一組依您國家匯率設定出來的價格,並使用以下語法︰
    "true","default_price_in_home_currency"
    If autofill is set to false, you need to specify a country and a price for each currency and you must use the following syntax:
    如果autofill被設為false,您就需要替每個國家依不同的匯率來決定價格,並使用底下語法︰
    "false", "home_country; default_price_in_home_currency; country_2; country_2_price; country_3; country_3_price; ..."
  • country The country for which you are specifying a price. You can only list countries that your application is targeting. The country codes are two-letter uppercase ISO country codes (such as "US") as defined by ISO 3166-2.
  • 國家 您指定價格的國家為何。您可以只設定想要販售的目標國家。國家代碼是大寫的2個字元(ISO國碼,像是"US"),這個國碼是被 ISO 3166-2定義和規範的格式。
  • price This is equivalent to the Price in the In-app Products UI. The price must be specified in micro-units. To convert a currency value to micro-units, you multiply the real value by 1,000,000. For example, if you want to sell an in-app item for $1.99 you specify 1990000 in the price field.
  • 價格 這個值等同於iap產品使用介面裡的價格。必須指定為微量單位(micro-units)。若需要將當下匯率轉換成微量單位,請乘上1,000,000。假如您想要賣的商品價格為美金$1.99,那這個值就是1990000。
Table 1. Language codes you can use with the locale field.
表1. 地區欄位裡您可以使用的語系代碼
Language Code Language Code
Chinese zh_TW Italian it_IT
Czech cs_CZ Japanese ja_JP
Danish da_DK Korean ko_KR
Dutch nl_NL Norwegian no_NO
English en_US Polish pl_PL
French fr_FR Portuguese pt_PT
Finnish fi_FI Russian ru_RU
German de_DE Spanish es_ES
Hebrew iw_IL Swedish sv_SE
Hindi hi_IN -- --

To import the items that are specified in your CSV file, do the following:
如果想要匯入您指定的CSV檔,請照以下方式︰
  1. Log in to your publisher account.
  2. 登入您的發佈帳戶
  3. In the All Android Market listings panel, under the application name, click In-app Products.
  4. 所有Adroid市集列表區塊中,應用程式名稱的底下,點擊應用程式內商品
  5. On the In-app Products List page, click Choose File and select your CSV file. The CSV file must be on your local computer or on a local disk that is connected to your computer.
  6. 在iap產品列表頁裡,點擊選擇檔案,然後選擇您的CSV檔。CSV檔必須存放在您本地端的電腦裡或者連結至您電腦的本地端硬碟中。
  7. Select the Overwrite checkbox if you want to overwrite existing items in your product list. This option overwrites values of existing items only if the value of the product_id in the CSV file matches the In-app Product ID for an existing item in the product list. Overwriting does not delete items that are on a product list but not present in the CSV file.
  8. 如果您想要覆寫已存在在您產品列表中的商品,請選擇覆寫選項。這個覆寫時機是在當iap產品列表裡的某些產品ID和CSV檔裡的product_id相同時。所謂的覆寫不會刪除存在在產品列而沒有存在在CSV檔裡的商品。
  9. On the In-app Products List page, click Import from CSV.
  10. 在iap產品列表頁面,點撃從CSV匯入
You can also export an existing product list to a CSV file by clicking Export to CSV on the In-app Product List page. This is useful if you have manually added items to a product list and you want to start managing the product list through a CSV file.
您也可以使用iap產品列表頁的匯出至CSV功能將既有的產品列表匯出成CSV檔。如果您已經手動新增商品至產品列表,然後您想要開始透過CSV檔管理您的產品項目時,這個方法會很有用。

Choosing a Purchase Type選擇商品的購買型態

An item's purchase type controls how Android Market manages the purchase of the item. There are two purchase types: "managed per user account" and "unmanaged."
Items that are managed per user account can be purchased only once per user account. When an item is managed per user account, Android Market permanently stores the transaction information for each item on a per-user basis. This enables you to query Android Market with the RESTORE_TRANSACTIONS request and restore the state of the items a specific user has purchased.
商品的購買型態控制了Android市集要以何種方式來管理該商品的購買行為。這裡有2種購買型態,分別為︰「受管理(依用帳戶)」和「不受管理」。經使用帳戶管理的商品僅能被每位使用者購買一次。當商品在這種狀態下, Android市集會以每個使用者當基礎來替每件商品儲存交易資訊,而且會被永久儲存。這種商品型態讓您可以透過發出RESTORE_TRANSACTIONS請求來跟Android市集查詢,並且能針對特定使用者(再次安裝APP時)還原該商品為已購買的狀態。
If a user attempts to purchase a managed item that has already been purchased, Android Market displays an "Item already purchased" error. This occurs during checkout, when Android Market displays the price and description information on the checkout page. When the user dismisses the error message, the checkout page disappears and the user returns to your user interface. As a best practice, your application should prevent the user from seeing this error. The sample application demonstrates how you can do this by keeping track of items that are managed and already purchased and not allowing users to select those items from the list. Your application should do something similar—either graying out the item or hiding it so that it cannot be selected.
如果使用者試圖購買一件被管理的商品,但是該商品他早就買過了,Android市集就會顯示出""商品已經買過了"的錯誤訊息。這個訊息會在當Android市集要在付費頁面顯示價格和商品描述資訊的付費流程中發生。當使用者沒看到這個錯誤訊息時,付費頁面卻消失了,畫面返回您AP的使用介面,這種狀況下,最好的方式我們認為︰您的APP根本不應該讓使用者看到該錯誤訊息!範例程式有說明您可以如何做到被管理類型的商品做出商品追蹤,並且直接將購買過的商品在APP列表裡隱藏。您現在要實作iap機制的APP也應該如此 - 將那些已經買過的商品反灰或隱藏、甚至是設成無法被點選的狀態吧!
The "manage by user account" purchase type is useful if you are selling items such as game levels or application features. These items are not transient and usually need to be restored whenever a user reinstalls your application, wipes the data on their device, or installs your application on a new device.
如果您現在要販售的是遊戲等級或應用程式的特殊功能,「被使用帳戶管理」的類型商品是很有用的。這些商品不會被傳輸、而且通常需要被還原,無論是使用者再度安裝您的APP、或者使用者清除了他們的裝置資料、甚至是在新的裝置上安裝您的APP時,都很有用。
Items that are unmanaged do not have their transaction information stored on Android Market, which means you cannot query Android Market to retrieve transaction information for items whose purchase type is listed as unmanaged. You are responsible for managing the transaction information of unmanaged items. Also, unmanaged items can be purchased multiple times as far as Android Market is concerned, so it's also up to you to control how many times an unmanaged item can be purchased.
「不被管理的商品」,他們的交易資訊不會被儲存在Android市集裡。這意謂著您無法針對購買商品類型被設為"不被管理"的商品,向Android市集做查詢交易資訊的動作。此時,這些不被管理商品的交易資訊,管理責任就落在您的手上了。而且,不被管理的商品可以被無限次數購買,所以,這種類型的商品倒底能被購買幾次,完全交在您的手裡。
The "unmanaged" purchase type is useful if you are selling consumable items, such as fuel or magic spells. These items are consumed within your application and are usually purchased multiple times.
如果您販賣的是消費型商品,像是燃料或者魔法法術,「不被管理」的商品類型就變得很有用了。這些商品都是在您APP裡的消耗型商品,而且通常會被購買多次。

Handling Refunds退費的處理

In-app billing does not allow users to send a refund request to Android Market. Refunds for in-app purchases must be directed to you (the application developer). You can then process the refund through your Google Checkout merchant account. When you do this, Android Market receives a refund notification from Google Checkout, and Android Market sends a refund message to your application. For more information, see Handling IN_APP_NOTIFY messages and In-app Billing Pricing.
iap機制不允許使用者發送退費請求至Android市集的。應用程式內商品的退費完完全全主導於您(APP的開發者)。您可以透過您的Google Checkout merchant帳戶來處理退費流程。當您執行了商品退費,Android市集就會接收到從Google Checkout傳來的退費通知,接著Android市集就會發送商品遭退費的訊息給使用者的APP。更多資訊請見 Handling IN_APP_NOTIFY messagesIn-app Billing Pricing這兩篇。
Important: You cannot use the Google Checkout API to issue refunds or cancel in-app billing transactions. You must do this manually through your Google Checkout merchant account. However, you can use the Google Checkout API to retrieve order information.
重要︰您無法使用Google Checkout 的API來處理退費或取消iap交易。您必須以手動方式透過Google Checkout merchant帳戶來處理這些事。然而,您仍然可以使用Google Checkout API來接收訂單資訊。

Setting Up Test Accounts設定測試帳戶

The Android Market publisher site lets you set up one or more test accounts. A test account is a regular Google account that you register on the publisher site as a test account. Test accounts are authorized to make in-app purchases from applications that you have uploaded to the Android Market site but have not yet published.
Android市集發佈網站讓您可以設定一或多組的測試帳號。所謂的測試帳號就是一個標準的Google帳號,您只是將它註冊至發佈網站成為測試帳戶而已。測試帳戶是被驗証的,因此您才可以透過上傳卻未發佈的APP來做出iap購買請求。
You can use any Google account as a test account. Test accounts are useful if you want to let multiple people test in-app billing on applications without giving them access to your publisher account's sign-in credentials. If you want to own and control the test accounts, you can create the accounts yourself and distribute the credentials to your developers or testers.
您可以使用任何的Google帳戶來當測試帳戶。如果您想要讓多個人測試您APP的iap機制,而您不想要把您發佈網站的登入帳戶給他們來使用時,測試帳戶就變得很有用了。如果您想要自己擁有也控制測試帳戶,您可以自行建立帳戶,並且將這組帳戶設成開發者帳戶或測試者帳戶。

Test accounts have three limitations:
測試帳戶有底下的三種限制︰
  • Test account users can make purchase requests only within applications that are already uploaded to your publisher account (although the application doesn't need to be published).
  • 測試帳戶的使用者只能在已上傳至您發佈帳戶的APP做iap購買請求。(即使APP不需要被真正發佈出去)
  • Test accounts can only be used to purchase items that are listed (and published) in an application's product list.
  • 測試帳戶僅能被用來購買那些被列在APP產品列表上(而且也被發佈出去)的商品上。
  • Test account users do not have access to your publisher account and cannot upload applications to your publisher account.
  • 測試帳戶的使用者無法存取您的發佈帳戶,也無法上傳APP至您的發佈帳戶裡。 
     
To add test accounts to your publisher account, follow these steps:
新增測試帳戶至您的發佈帳戶裡,請照以下方式︰
  1. Log in to your publisher account.
  2. 登入您的發佈帳戶。
  3. On the upper left part of the page, under your name, click Edit profile.
  4. 在頁面上方的左側,您的名字底下,點擊編輯個人資料
  5. On the Edit Profile page, scroll down to the Licensing & In-app Billing panel (see figure 5).
  6. 在編輯個人資料的頁面中,頁面下滑至授權和應用程式內結帳(見圖5)。
  7. In Test Accounts, add the email addresses for the test accounts you want to register, separating each account with a comma.
  8. 在測試帳戶中,新增您想註冊的測試帳戶的e-mail,多個帳戶請用逗號隔開。
  9. Click Save to save your profile changes.
  10. 點擊儲存來儲存變更。

Figure 5. The Licensing and In-app Billing panel of your account's Edit Profile page lets you register test accounts. 
圖5.  這是您帳戶中編輯個人資料裡的授權和應用程式內結帳區塊,您可以在這裡註冊測試帳戶。

Where to Get Support在哪裡尋求支援

If you have questions or encounter problems while implementing in-app billing, contact the support resources listed in the following table (see table 2). By directing your queries to the correct forum, you can get the support you need more quickly.
如果您在實作iap機制時有問題或者遇到問題 ,可以聯絡表格中列出的支援的資源列表(見表2)。依您的需求尋求適合的論壇,您可以更快速地獲得您所需要的支援。

Table 2. Developer support resources for Android Market in-app billing.
表2. Android市集iap機制開發者支援的資源。
Support Type支援的型態 Resource資源 Range of Topics主題的範圍
Development and testing issues開發與測試問題 Google Groups: android-developers In-app billing integration questions, user experience ideas, handling of responses, obfuscating code, IPC, test environment setup.
iap機制的整合問題、使用者經驗發想、 處理回應、模糊程式碼、內部進程溝通、測試環境的設定。
Stack Overflow: http://stackoverflow.com/questions/tagged/ android
Market billing issue tracker市集金流問題追蹤 Market billing project issue tracker Bug and issue reports related specifically to in-app billing sample code.
關於iap機制範例程式的BUG與問題回報
For general information about how to post to the groups listed above, see Developer Forums document in the Resources tab.
若想知道如何發文至上面的群組論壇的基本資訊,請見Android API裡Resources頁裡的Developer Forums 文章。

相關文章︰
1.[Android in-app billing前言]In-app Billing應用程式內部付費機制(中文翻譯)
2.[Android in-app billing第1篇]In-app Billing Overview應用程式內部付費機制概述(中文翻譯)
3.[Android in-app billing第2篇]Implementing In-app Billing實作應用程式內部金流機制(中文翻譯)
4.[Android in-app billing第3篇]Security and Design安全與設計(中文翻譯)
5.[Android in-app billing第4篇]Testing In-app Billing測試應用程式內金流機制(中文翻譯)
6.[Android in-app billing第5篇]Administering In-app Billing應用程式內金流機制的管理(中文翻譯)
7.[Android in-app billing第6篇(末)]In-app Billing Reference應用程式金流的相關API(中文翻譯)

Wednesday, December 21, 2011

[Android in-app billing第4篇]Testing In-app Billing測試應用程式內金流機制(中文翻譯)

了解iap測試工具是如何運作,並學習如何測試你實作出來的iap機制。

原文連結︰Testing In-app Billing
翻譯︰小鰻
翻譯版本號︰v.1.0
如需轉載請註明出處「小鰻的Android學習筆記
讓我參與最直接的討論以及錯誤修正, 謝謝!

In this document

  1. Testing in-app purchases with static responses
  2. Testing in-app purchases using your own product IDs

Downloads

  1. Sample Application

See also

  1. Overview of In-app Billing
  2. Implementing In-app Billing
  3. Security and Design
  4. Administering In-app Billing
  5. In-app Billing Reference
The Android Market publisher site provides several tools that help you test your in-app billing implementation before it is published. You can use these tools to create test accounts and purchase special reserved items that send static billing responses to your application.
Android市集軟體發佈網站提供了數個工具,幫助您在發佈APP以前,針對您實作的iap機制做測試。您可以使用這些工具來建立測試帳戶以及透過發送靜態性質的金流回應(static billing responses)至您的APP來購買那些已已先設置在網站內的特殊商品。

To test in-app billing in an application you must install the application on an Android-powered device. You cannot use the Android emulator to test in-app billing. The device you use for testing must run a standard version of the Android 1.6 or later platform (API level 4 or higher), and have the most current version of the Android Market application installed. If a device is not running the most current Android Market application, your application won't be able to send in-app billing requests to Android Market. For general information about how to set up a device for use in developing Android applications, see Using Hardware Devices.
如果要在您的APP裡測試iap機制,您必須在實際裝置上安裝您的APP,因為您無法使用模擬器來測試iap機制。並且,您用來測試的裝置也有以下條件︰Android1.6以上的標準Android版本、安裝了最新版的Android市集。如果您的Android市集軟體並非最新,也許您的APP就無法透過Android市集軟體發送出iap金流請求。關於如何設定一個用來開發Android軟體的裝置,請參見Using Hardware Devices這篇文章。

The following section shows you how to set up and use the in-app billing test tools.
接下來的章節將會教您如何設定並且使用iap金流測試工具。

Testing in-app purchases with static responses使用靜態回應的方式測試iap購買機制

We recommend that you first test your in-app billing implementation using static responses from Android Market. This enables you to verify that your application is handling the primary Android Market responses correctly and that your application is able to verify signatures correctly.
我們建議您在第1次使用iap機制時,跑一下靜態回應(static responses)這個流程。這能幫助您去驗証您的APP是否有對Android市集傳來的主要回應做出正確的處理,以及您的APP是否能正確的驗証數位簽章。

To test your implementation with static responses, you make an in-app billing request using a special item that has a reserved product ID. Each reserved product ID returns a specific static response from Android Market. No money is transferred when you make in-app billing requests with the reserved product IDs. Also, you cannot specify the form of payment when you make a billing request with a reserved product ID. Figure 1 shows the checkout flow for the reserved item that has the product ID android.test.purchased.
如果要在靜態回應的環境底下去實作iap機制,您必須使用一些已預先設置的產品ID來做金流請求測試。每個已預先設置的產品ID皆會回傳一個特殊的靜態回應,而且不會有任何金錢上的交易發生。並且,您如果使用金流機制去請求購買這個已預先設置的產品ID,您就無法指定付款的方式。圖1顯示購買已預先設置的商品、產品ID為android.test.purchased的付費流程。

Figure 1. Checkout flow for the special reserved item android.test.purchased. 
圖1. 這是已預先設置的特殊商品︰android.test.purchased的付費流程。

You do not need to list the reserved products in your application's product list. Android Market already knows about the reserved product IDs. Also, you do not need to upload your application to the publisher site to perform static response tests with the reserved product IDs. You can simply install your application on a device, log into the device, and make billing requests using the reserved product IDs.
您不需要在您軟體發佈網站上的APP產品列表裡列出這些已預先設置的商品,Android市集已經知道這些商品了。 您也不需要在您執行靜態回應測試這些已預設的商品ID上,將您的APP真實的發佈出去。您可以很簡單的僅將APP安裝在裝置上,寫出裝置的log,並且發出這些已預設的商品的金流請求。

There are four reserved product IDs for testing static in-app billing responses:
底下有4組已預先設置好的產品ID,提供您做靜態iap機制回應的測試︰
  • android.test.purchased When you make an in-app billing request with this product ID, Android Market responds as though you successfully purchased an item. The response includes a JSON string, which contains fake purchase information (for example, a fake order ID). In some cases, the JSON string is signed and the response includes the signature so you can test your signature verification implementation using these responses.
    android.test.purchased
    當您使用這個產品ID來發出金流請求時,Android市集會發出一個虛擬的購買商品成功回應給您。這個回應包含了JSON字串,這個字串含蓋了假的購買資訊(舉例︰一個假的訂單ID)。在一些例子中,JSON字串是被簽署並且會回應一個含有數位簽章的字串給您的,因此您可以透過這些虛擬的回應,來完成您想要測試驗証數位簽章的動作。
  • android.test.canceled When you make an in-app billing request with this product ID Android Market responds as though the purchase was canceled. This can occur when an error is encountered in the order process, such as an invalid credit card, or when you cancel a user's order before it is charged.
    android.test.canceled
    當您使用了這個產品ID來發送金流請求時,Android市集會回應一個類似真正購買過程遭取消的反應給您。這可能發生當使用者在訂單流程中,發生了錯誤的狀況下。像是使用者使用了錯誤的信用卡、或者在付費之前,使用者按下了取消按鈕。
  • android.test.refunded When you make an in-app billing request with this product ID, Android Market responds as though the purchase was refunded. Refunds cannot be initiated through Android Market's in-app billing service. Refunds must be initiated by you (the merchant). After you process a refund request through your Google Checkout account, a refund message is sent to your application by Android Market. This occurs only when Android Market gets notification from Google Checkout that a refund has been made. For more information about refunds, see Handling IN_APP_NOTIFY messages and In-app Billing Pricing.
    android.test.refunded
    當您使用了這個產品ID來發送金流請求時,Android市集會回應一個類似真實的產品被退費的反應給您。商品退費是無法透過Android市集的iap機制服務來完成的(需使用merchant網站來退費)。在您透過Google Checkout 帳戶跑完商品退費流程,退費訊息就會經由Android市集發送至您的APP裡。這只會發生在Google Checkout網站退費動作發生的情況下,Android市集才有可能會接收到此退費的訊息通知。更多關於退費的資訊,請參照Handling IN_APP_NOTIFY messagesIn-app Billing Pricing

  • android.test.item_unavailable When you make an in-app billing request with this product ID, Android Market responds as though the item being purchased was not listed in your application's product list.
    android.test.item_unavailable
    當您使用這個產品ID做出金流請求時,Android市集會回應類似您發送了一個發佈網站裡沒有列出的內部商品的購買請求的反應給您。
In some cases, the reserved items may return signed static responses, which lets you test signature verification in your application. To test signature verification with the special reserved product IDs, you may need to set up test accounts or upload your application as a unpublished draft application. Table 1 shows you the conditions under which static responses are signed.
在一些案例中,這些已預先設置的商品也許會返回靜態回應簽署,提供您在您APP當中,以測試的方式驗証您的數位簽章。如果想要測試驗証數位簽章和這些已預先設置的產品ID,您必須先設定好您的測試帳戶或者上傳您的APP草稿版本。表1顯示那些被簽署過的靜態回應底下的狀況。

Table 1. Conditions under which static responses are signed.
表1.在被簽署過後的靜態回應底下的狀況。
Application ever been published?
APP是否曾經發佈過?
Draft application uploaded and unpublished?
草稿APP上傳了且無須發佈?
User who is running the application
執行APP的人是誰
Static response signature
靜態回應簽章
No No Any任何人 Unsigned未簽署
No No Developer開發者 Signed已簽署
Yes No Any任何人 Unsigned未簽署
Yes No Developer開發者 Signed已簽署
Yes No Test account測試帳戶 Signed已簽署
Yes Yes Any任何人 Signed已簽署
To make an in-app billing request with a reserved product ID, you simply construct a normal REQUEST_PURCHASE request, but instead of using a real product ID from your application's product list you use one of the reserved product IDs.
如果要針對已預先設置的產品ID發送iap金流請求, 您只要簡單的建構一般REQUEST_PURCHASE的請求即可。但是請不要使用您真實的產品列表上的產品ID。

To test your application using the reserved product IDs, follow these steps:
若要在您的APP裡使用這些已預先設置的產品ID,請照著底下的步驟走︰
  1. Install your application on an Android-powered device. You cannot use the emulator to test in-app billing; you must install your application on a device to test in-app billing.
    To learn how to install an application on a device, see Running on a device.
  2. 安裝您的APP至實際裝置上。您不能使用模擬器來測試iap機制,您必須安裝您的APP至裝置上,方可測試使用iap機制。
  3. Sign in to your device with your developer account. You do not need to use a test account if you are testing only with the reserved product IDs.
  4. 將您的裝置登入成您的開發者帳戶。如果您只是想要測試已預先設置的產品ID,您就不需要一定將您的手機設成測試帳戶。
  5. Verify that your device is running a supported version of the Android Market application or the MyApps application. If your device is running Android 3.0, in-app billing requires version 5.0.12 (or higher) of the MyApps application. If your device is running any other version of Android, in-app billing requires version 2.3.4 (or higher) of the Android Market application. To learn how to check the version of the Android Market application, see Updating Android Market.
  6. 請去驗証您的裝置安裝的Android市集或MyApps的版本號有支援iap機制。如果您的裝置運行Android3.0版,需要MyApps軟體版號在5.1.12(或更高)。如果您的裝置運行其它Android的版本,iap機會需要Android市集軟體版號在2.3.4(或更高)。如果想學習如何查看您Android市集軟體的版號,請參見Updating Android Market
  7. Run your application and purchase the reserved product IDs.
  8. 運行您的APP並且購買這些已預先設置好的產品IDs。
Note: Making in-app billing requests with the reserved product IDs overrides the usual Android Market production system. When you send an in-app billing request for a reserved product ID, the quality of service will not be comparable to the production environment.
註︰已預設產品ID的iap請求發送不屬於Android市集產品系統的涵蓋範圍內。當您發送一筆已預設產品ID的iap請求時,統計數據不會被納入產品統計服務裡。(譯者註︰此段僅供參考><看不太懂)

Testing In-app Purchases Using Your Own Product IDs

使用您自己的產品ID來測試iap購買機制

After you finish your static response testing, and you verify that signature verification is working in your application, you can test your in-app billing implementation by making actual in-app purchases. Testing real in-app purchases enables you to test the end-to-end in-app billing experience, including the actual responses from Android Market and the actual checkout flow that users will experience in your application.
當您完成了靜態回應測試,您也驗証了數位簽章,一切就緒後,您就可以開始實際上的發出您實作iap購買請求了。 測試實際的iap購買機制能夠讓您有一個端點(end-to-end)的iap體驗,包含從Android市集來的真實回應、以及使用者真正您APP裡經驗到的真實的付款流程。

Note: You do not need to publish your application to do end-to-end testing. You only need to upload your application as a draft application to perform end-to-end testing.
To test your in-app billing implementation with actual in-app purchases, you will need to register at least one test account on the Android Market publisher site. You cannot use your developer account to test the complete in-app purchase process because Google Checkout does not let you buy items from yourself. If you have not set up test accounts before, see Setting up test accounts.
註︰您不需要發佈您的APP來做點對點測試(end-to-end teseting),您只需要以草稿的型式來上傳您的APP。如果要測試您APP真實的iap機制,您會需要註冊至少一組的測試帳戶至Android市集發佈網站。您無法使用您的開發者帳號來測試完整的iap購買流程,因為Google Checkout無法讓您購買您自己的商品。如果您之前沒有設定過測試帳戶,那麼請看Setting up test accounts這篇。

Also, a test account can purchase an item in your product list only if the item is published. The application does not need to be published, but the item does need to be published.
而且,測試帳戶只能購買那些您商品列表中已被發佈的商品。您的APP不需要真的被發佈,但是商品絕對需要被發佈。
When you use a test account to purchase items, the test account is billed through Google Checkout and your Google Checkout Merchant account receives a payout for the purchase. Therefore, you may want to refund purchases that are made with test accounts, otherwise the purchases will show up as actual payouts to your merchant account.
To test your in-app billing implementation with actual purchases, follow these steps:
當您使用測試帳戶來購買商品,測試帳戶就會透過Google Checkout產生消費,您的Google Checkout Merchant帳戶接著會收到購買的付款款項。因此,您也許會想要將剛才在測試帳戶裡的消費做退款動作,否則您的測試用的消費記錄會真的記在您merchant帳戶裡。如果要測試您實作出來的iap機制的真實購買情形,可以照著以下的步驟做︰
  1. Upload your application as a draft application to the publisher site. You do not need to publish your application to perform end-to-end testing with real product IDs; you only need to upload your application as a draft application. However, you must sign your application with your release key before you upload it as a draft application. Also, the version number of the uploaded application must match the version number of the application you load to your device for testing. To learn how to upload an application to Android Market, see Uploading applications.
  2. 上傳您的草稿APP至發佈網站。您無需發佈您的APP才能執行端點測試和真實產品ID的消費。您僅需以草稿的方式將您的APP上傳。然而,您必須將您的APP簽署上那把你平時釋出APP時,專用的金鑰。而且,您上傳的APP版號必須和你裝置上要執行測試的APP的版號一致。如果想知道關於如何上傳APP至Android市集,請見 Uploading applications
  3. Add items to the application's product list. Make sure that you publish the items (the application can remain unpublished). See Creating a product list to learn how to do this.
  4. 新增商品至APP產品列表上。請確定您已將商品發佈(APP可保持未發佈狀態)。請見Creating a product list學習如何新增商品。
  5. Install your application on an Android-powered device. You cannot use the emulator to test in-app billing; you must install your application on a device to test in-app billing.
    To learn how to install an application on a device, see Running on a device.
  6. 安裝您的APP至Android實機上。您無法使用模擬器來測試iap機制。
  7. Make one of your test accounts the primary account on your device. To perform end-to-end testing of in-app billing, the primary account on your device must be one of the test accounts that you registered on the Android Market site. If the primary account on your device is not a test account, you must do a factory reset of the device and then sign in with one of your test accounts. To perform a factory reset, do the following:
  8. 設定一組測試帳戶至您的裝置上,且該帳戶要是裝置的主要帳戶。如果要執行iap的端點測試,您就必須將一組您已註冊至Android市集網站的測試帳戶設定至裝置上,且要是主要帳戶。如果目前您的裝置上,測試帳戶不是主要的帳戶,那麼請您使用回復原廠設定,並重新做測試帳戶的登入設定。如困要執行回復原廠設定,請照著以下做︰
    1. Open Settings on your device.
    2. 開啟裝置上的設定
    3. Touch Privacy.
    4. 點擊隱私設定
    5. Touch Factory data reset.
    6. 點擊重設為原廠設定
    7. Touch Reset phone.
    8. 點擊重設手機
    9. After the phone resets, be sure to sign in with one of your test accounts during the device setup process.
    10. 在您的手機重設後,請確認已在裝置的設定流程裡,將測試帳戶設定進去了。
  9. Verify that your device is running a supported version of the Android Market application or the MyApps application. If your device is running Android 3.0, in-app billing requires version 5.0.12 (or higher) of the MyApps application. If your device is running any other version of Android, in-app billing requires version 2.3.4 (or higher) of the Android Market application. To learn how to check the version of the Android Market application, see Updating Android Market.  
  10. 請驗証您的裝置運行的Android市集軟體或MyApps軟體版號有支援iap機制。如果您的裝置運行Android3.0,請確認版號在5.0.12(或更高),如果是其它的Android版本,Android市集軟體版號需求是2.3.4(或更高)。如果想知道如何查看Android市集軟體的版號,請見Updating Android Market
  11. Make in-app purchases in your application.
  12. 在您的APP裡運行iap購買。
Note: The only way to change the primary account on a device is to do a factory reset, making sure you log on with your primary account first.
When you are finished testing your in-app billing implementation, you are ready to publish your application on Android Market. You can follow the normal steps for preparing, signing, and publishing your application
註︰唯一將裝置上帳戶設成主要帳戶的方式就是重設為原廠設定,請務必確定您將測試帳戶登入成主要帳戶了。
當您完成了您實作的iap金流測試,您就可以開始準備將您的APP發佈至Android市集了。您可以照著一般流程來完成發佈︰preparing, signingpublishing your application

相關文章︰
1.[Android in-app billing前言]In-app Billing應用程式內部付費機制(中文翻譯)
2.[Android in-app billing第1篇]In-app Billing Overview應用程式內部付費機制概述(中文翻譯)
3.[Android in-app billing第2篇]Implementing In-app Billing實作應用程式內部金流機制(中文翻譯)
4.[Android in-app billing第3篇]Security and Design安全與設計(中文翻譯)
5.[Android in-app billing第4篇]Testing In-app Billing測試應用程式內金流機制(中文翻譯)
6.[Android in-app billing第5篇]Administering In-app Billing應用程式內金流機制的管理(中文翻譯)
7.[Android in-app billing第6篇(末)]In-app Billing Reference應用程式金流的相關API(中文翻譯)
8.[Android in-app billing筆記]串接Google play in-app billing易犯的錯誤