インストールリファラでハマった話

Post on 24-May-2015

949 Views

Category:

Engineering

8 Downloads

Preview:

Click to see full reader

DESCRIPTION

potatotips #6 で発表した内容。

TRANSCRIPT

インストールリファラで ハマった話

2014/4/9 @sakebook

http://sakebook.blogspot.com https://github.com/sakebook

開発環境でテスト

adb shell am broadcast -a com.android.vending.INSTALL_REFERRER -n PKG_NAME/.MyBroadcastReceiver —es referrer utm_campaign%3Dsample_campaign

テストをパスしたため本番公開

本番で不具合

\(^o^)/

開発環境では再現しないが 本番環境では再現する

α/β版テスト機能

既存ユーザに影響を与える事 無く本番環境でテストができる※バージョンはapkアップロードの度上昇し、戻せない

ここから本題

開発環境と本番環境では 何が違ったのか?

ActivityとBroadcastは 別スレッドで走る

Broadcastが先行するとは限らない!

adbを用いるため 必ずBroadcastが先行!

• $ adb ~

• BroadcastReceiver#onReceive

• アプリ起動

• Activity#onCreate

• アプリ起動

• Activity#onCreate

• ↕️

• BroadcastReceiver#onReceive

開発環境 本番環境

Activityの状態を監視しよう (オブザーバー)

ActivityがBroadcastからの通知を受け取る準備が できてない状態で通知をしようとするため

通知に失敗する。 !

Activityが自分のタイミングで 通知を受け取るようにする。

public class GooglePlayReceiver extends BroadcastReceiver{! @Override public void onReceive(Context context, Intent intent) { ….! if (!TextUtils.isEmpty(campaign)) { SharedPreferences preferences = PreferenceManager.getDefaultSharedPreferences(context); preferences.edit().putString("referrer", campaign).commit();! MyObserver.getInstance().notifyObserver(); } }}

Broadcast

public class MyObserver{ private static MyObserver ourInstance = new MyObserver(); private static List<ReceiveObserver> mObservers = new CopyOnWriteArrayList<ReceiveObserver>(); …. public void notifyObserver() { /* 登録されている全監視対象に変更を通知 */ for (int i=0; i<mObservers.size(); i++) { mObservers.get(i).onReceived(); } } ….}

Observer

public class MainActivity extends ActionBarActivity implements ReceiveObserver{! @Override protected void onCreate(Bundle savedInstanceState) { … /* 呼ばれても良い状態になったら監視対象にする */ MyObserver.getInstance().addObserver(this); doSomeThing(); }! @Override public void onReceived() { /* 監視対象から外す */ MyObserver.getInstance().removeObserver(this); doSomeThing(); }! private void doSomeThing() { /* 通常起動、及びReceiverスレッドより先行した場合はリファラがない。 */ if (TextUtils.isEmpty(referrer)) { return; } /* 本当にしたいこと */ }}

Activity

まとめ

・本番でしか再現できないときはα/β版で試そう ・ActivityとBroadcastは別スレッドで 動くので制御が必要 !

以上

サンプルコード https://github.com/sakebook/android-sample-referrertest

top related