これは、Nexus 7 タブレットで実行されているアプリでアイテムを購入し、Nexus One スマートフォンで実行されている同じアプリを使用してその購入を検出した私自身の経験です。以下で説明するテストは、ドラフト モードでアップロードされた (まだ公開されていない) アプリのテスト アカウントを使用して実行されました。テスト アカウントは、ドラフト アプリの開発者コンソールで宣言され、両方のテスト デバイスのメイン アカウントでした。
行われた購入は非消耗品でした。購入は、TrivialDrive サンプル アプリで提供される IabHelper クラスのバリアントを使用して行われました。購入を行うために呼び出された IabHelper メソッドは launchPurchaseFlow() でした。
購入が行われるとすぐに、IabHelper の queryInventoryAsync() メソッドがその後使用されたときに、同じデバイスに返された購入済みアイテムのリストにアイテムが追加されました。
ただし、同じアカウントが所有する別の Nexus One デバイスは、起動時に queryInventoryAsync() の呼び出しを実行しましたが、そのメソッドを使用して返された購入済みアイテムのインベントリで購入済みアイテムを受け取りませんでした。
ただし、Nexus One デバイスを使用して launchPurchaseFlow() を使用して同じアイテムの購入を開始した場合、メッセージが返されました (購入に使用されたであろうディスプレイの前にポップアップしたダイアログで)、すでに所有しているため、購入できないことを示します。これは、Nexus 7 から購入が開始されてから 15 分も経たないうちに発生しました。これは、データが Google Play サーバーでかなり迅速に利用可能になったことを示していますが、Nexus One ではアイテムを再購入しようとするまで自動的に利用可能ではなかったことを示しています。 Nexus One デバイスが開始されました。
すでに所有しているアイテムを購入しようとするこの失敗した試みに続いて、Nexus One でのその後の queryInventoryAsync() の呼び出しでアイテムが表示されました。これは、アイテムを購入しようとしたことで、Nexus One Google Play アプリのバッファリングされたデータと Google Play サーバーで利用可能なデータとの同期がトリガーされたことを示唆しています。これは、queryInventoryAsync() 自体によってトリガーされたものではありません。
Nexus One から既に所有しているアイテムを購入しようとする代わりに、Google Play アプリのキャッシュを削除する 2 番目のシナリオをテストしました。これは、queryInventoryAsync() によって返されたデータの更新を開始しませんでした。そのデータは変更されませんでした。
Nexus One から既に所有しているアイテムを購入しようとする代わりに、単に Nexus One の電源を切ってから再度電源を入れるという 3 番目のシナリオをテストしました。この後、同じアプリを実行して queryInventoryAsync() リクエストを実行すると、Nexus 7 から購入したアイテムが、返された購入済みアイテムのリストに実際に表示されました。
上記のことから、Google Play アプリは、購入をローカルにバッファリングし、特定のトリガーが発生したときにのみ更新することで、Google Play サーバーへの往復回数を減らそうとしていると結論付けています。1) 既に所有しているアイテムを購入しようとする試み、および 2) Google Play アプリが実行されているデバイスの再起動の 2 つのトリガーを特定しました。特に、 queryInventoryAsync() はそのような更新を開始しないため、上記のように古いデータが返される場合があります。
上記のことを知っていれば、Google Play サーバーで利用可能なデータからバッファリングされたデータの更新を意図的にトリガーできるため、テストがより効率的になり、混乱が少なくなります。