BillingServiceの停止について

660 views
Skip to first unread message

PetitPetit

unread,
Feb 5, 2012, 10:14:03 PM2/5/12
to 日本Androidの会
初めまして、PetitPetitと申します。

現在、アプリ内課金の実装に取り組んでいるのですが、設定>アプリ>実行中のサービスから確認したところ、アプリ本体は終了している
(onDestroyが呼ばれている)にもかかわらずBillingServiceが動いたままになっています。
これを停止させようと以下のようにBillingService.javaのunbindメソッドでstopSelfメソッドを呼んでみました。

public void unbind() {
try {
unbindService(this);
stopSelf();
} catch (IllegalArgumentException e) {
// This might happen if the service was disconnected
}
}

しかし実行中のサービスには相変わらずBillingServiceが表示されており、BillingServiceのonDestroyも呼ばれてお
らず、停止処理そのものが行われていないようです。
試しにサンプルアプリ(Dungeons)を未修正でインストールしてみたところ、こちらもBillingServiceは停止せず動いたままでし
た。

サンプルでも同じ現象になる以上サンプル自体のバグかと思うのですが、無駄に常駐サービスを増やしたくないのでなんとか停止させたいと思っています。
どなたか対処方法をご存知ではないでしょうか?

kacodama

unread,
Feb 6, 2012, 9:06:11 PM2/6/12
to 日本Androidの会
BillingServiceが起動していないと、キャンセルや払い戻し通知を(アプリを起動していないと)
受け取れないので、起動したままにしておくことが前提なのではないでしょうか。
バグではないと思います。少なくとも弊社ではこれを利用して実装しています。

BillingServiceを止める方法については、調べたことがないのでお力になれません・・・

PetitPetit

unread,
Feb 7, 2012, 1:29:01 AM2/7/12
to 日本Androidの会
kacodama様、返信ありがとうございます。

> BillingServiceが起動していないと、キャンセルや払い戻し通知を(アプリを起動していないと)
> 受け取れないので、起動したままにしておくことが前提なのではないでしょうか。

この点については考えていませんでした。
確かに、これらの通知がアプリを終了した時に送られて来ることは十分考えられますね。バグというのは早計だったかもしれません。
ただ、そうなるとアプリ内課金を実装しているアプリが複数インストールされていた場合、全てのアプリでBillingServiceが動き続けることに
なり、端末に大きな負荷がかかってしまいます(実際に試作段階のアプリとサンプルアプリ、両方でBillingServiceが動き続けていまし
た)。
そうなると全体的な動作の低下につながるので、やはり端末への負荷は最低限に抑えたいところですが・・・意図的にBillingServiceを常駐さ
せているとしたら、難しいかもしれないですね。

kacodama

unread,
Feb 7, 2012, 9:04:38 PM2/7/12
to 日本Androidの会
DevサイトのServiceのライフサイクルに関する記述では、
#(http://developer.android.com/intl/ja/guide/topics/fundamentals/
services.html)のManaging the Lifecycle of a Service

startServiceしたものはstopSelfで止める(止められる)
bindServiceしたものはシステムがbind数が0になったら勝手に止める

というように解釈できますが、どうなんでしょう?
弊社のアプリは、殺しても殺してもプロセスが勝手に立ち上がってきますので、BillingServiceのせいでOSが勝手に再起動しているのかなあ
と思っていたのですが・・・
アプリの画面が全て終了した際にはunBindを通っているので、0になっているはずなのですが。

ちょっとこの辺理解が私も曖昧です。

あとは、manifestファイルのserviceのところで、"android:enabled=false"にするとどうでしょう?
システムがサービスをインスタンス化できるかという設定のようですが・・・

PetitPetit

unread,
Feb 8, 2012, 2:21:32 AM2/8/12
to 日本Androidの会
> アプリの画面が全て終了した際にはunBindを通っているので、0になっているはずなのですが。

私が引っかかっているのも、まさにこの点です。
DungeonsアクティビティのonDestroyでunBindメソッドを呼んでいるのは、onCreateで生成した
BillingServiceのインスタンス(mBillingService)を破棄する目的だと考えています。
本来なら終了するはず(?)のタイミングで停止しないため、最初の投稿時に書いたようにstopSelfメソッドを呼んで直に停止させようと試みたので
すが、効果はありませんでした。
これは推測ですが、unBindした時点でBillingServiceのonDestroyメソッドが呼ばれないのは、他の何かが
mBillingServiceを参照しているからなのかもしれません。mBillingServiceを「何か」が必要としているので、
DungeonsアクティビティからunBindされても破棄されないのではと。
その「何か」を特定する、或いはそういうものが存在するかを確認するには、Serviceの仕組みやサンプルプログラムの動きについてもっと勉強する必
要がありそうです。

> あとは、manifestファイルのserviceのところで、"android:enabled=false"にするとどうでしょう?
試してみましたが、これは関係ないようですね・・・
むしろサンプルアプリ内でのログが更新されなくなったりと、必要なサービス起動まで阻害されてしまうようです。

今後もなんとか改善する方法はないか検討していくつもりですが、当面は課金画面を独立させるなどして、極力BillingServiceを起動させない
ように実装していこうと思います。

nagamatu

unread,
Feb 8, 2012, 2:56:55 AM2/8/12
to 日本Androidの会
% adb shell dumpsys

上記の出力から調べたい ServiceRecordを探し出して、IntentBindRecordの Clientが現在 Bindしているクライ
アントとなります。

--

PetitPetit

unread,
Feb 10, 2012, 2:01:46 AM2/10/12
to 日本Androidの会
>% adb shell dumpsys
以下の3パターンでこのコマンドを実行し、出力を比較してみました。

1. Dungeonsアクティビティ起動後
2. 1.の後、Dungeonsアクティビティ終了(購入リクエスト等の操作はなし)
3. DungeonsアクティビティのonCreate文で即座にunBind()を呼び、アクティビティは終了しない。

これらの出力を比較してわかったことをまとめると、このような感じです。

・BillingServiceの他に、MarketBillingServiceが起動されている。
・IntentBindRecordはMarketBillingServiceの出力にのみ存在し、BillingServiceにはない。
・2.の時点でMarketBillingServiceは停止している(BillingServiceは停止せず)
・BillingServiceのProcessRecordには1.の時点でMarketBillingServiceへの
ConnectionRecordが存在するが、2.になるとこれは失われる。
・3.の場合は各サービスは起動しないか、期待通りunBind()で停止する(出力なし)。

この結果を見ると、unBind()を呼ぶことで参照を破棄されているのはBillingServiceではなく、
MarketBillingServiceの方であるように思います。
だとすると、やはりkacodama様が仰るようにBillingServiceは「常に動いていることが前提」ということでしょうか。
しかしそうなると、今度は再起動しただけでその前提が覆ってしまう問題があります(再起動時にはBillinServiceは起動しないので)。
やはりサンプルのどこかに足りない部分がありそうな気がします。
Reply all
Reply to author
Forward
0 new messages