Firebaseのコンソールから送る通知(Notification)、いわゆるpushは、クライアントから受信をオフにすることは出来ません。
OS4.1以降ならアプリの設定から「通知」を切ればいいですが、旧OSで「通知が切れない、ウザい」とレビューを書かれるのを避けるには、アプリ内に設定を設けて、ユーザーがオフにしたときはサービス内で受信した通知を無視するコードを書くしかありません。
この方法で、アプリがフォアグラウンド時には無視できるのですが、問題はバックグラウンド時です。
バックグラウンド時の受信は、SDKが自動でやってしまうため、これをコードから「機能を停止させる」ことはどうやら出来ません。
疑似的にpushを無視する方法として、以下のパターンを考えました&見つけました。
- topic購読機能を利用する
- FirebaseAnalyticsのユーザープロパティを利用する
- priorityの高いレシーバークラスを作成して無視するコードを書く
- コンソールからの通知を行わず、FCMのみ利用する
1. topic購読機能を利用する
必ずtopic購読を指定する方法です。
もともと仕様上topicが複数ある場合はいいのですが、特に何も考えていない場合は、アプリからtopic購読・購読解除のコードを書く必要が本来はありません。
ここであえて"all"などのトピックを作成して、通知設定がONの時は購読、OFFの時は購読解除、とすることで、疑似的にpush受信のon/off設定に使うというわけです。
FirebaseMessaging.getInstance().subscribeToTopic("all");
FirebaseMessaging.getInstance().unsubscribeFromTopic("all");
コーディングは恐らく最も簡単な方法です。
注意点は、必ずtopicをターゲット指定した通知をコンソールから送るという運用ルールが必要になることです。
また、ユーザーセグメントを使ったターゲット指定を最初から考えている場合は、この手法はとらない方がいいです。
というのも、ユーザーセグメントをターゲットにした通知と、topicをターゲットにした通知が、同時に指定できないからです。
2. FirebaseAnalyticsのユーザープロパティを利用する
FirebaseAnalyticsに特定のuserPropertyを送り、それをユーザーセグメント指定のフィルタに利用する方法です。
mFirebaseAnalytics.setUserProperty("push_enabled", "true");
mFirebaseAnalytics.setUserProperty("push_enabled", "false");
※userPropertyは先にコンソールから登録すること
この方法も、1と同じく、必ずユーザープロパティ"push_enabled"="true"をフィルタにターゲット指定した通知をコンソールから送るという運用ルールが必要です。
この方法の難点として上げるならば、userPropertyによるフィルタリングがどの程度のタイムラグで行われるか分からないこと、です。
FirebaseAnalyticsの送信は定期的にまとめて行われているようで、反映に時間がかかることが分かっています。
数時間前に設定をoffにしたユーザーに、pushを打ったら届いちゃった、ということが発生する可能性は高いです。
3. priorityの高いレシーバークラスを作成して無視するコードを書く
こちらで紹介されていた方法です。
(http://stackoverflow.com/questions/37511198/firebase-on-android-i-want-to-disable-firebase-notifications-on-android-client)
WakefulBroadcastReceiverの派生クラスを登録して、設定がoffになっていたらabortBroadcast()
すればよいようです。(試してみていないです。)
長期の運用が予想されて、その運用がアプリ開発者の目の届かないところにいく可能性が高い場合は、運用ルールを必要とする1や2の方法はあまり好ましくありません。
なので、この方法を検討した方がいい気がしますが、コメントにも書かれているとおり、将来にわたって動作が保証されている手法ではないことに留意する必要があります。
4. コンソールからの通知を行わず、FCMのみ利用する
自前のサーバーからpushを打つ方法です。この方法はアプリに作成した自前の受信サービスのonMessageReceived
に必ず飛んできますから、自由にpushを無視できます。
難点は、サーバー開発担当者が必要になることでしょうか。
Firebaseのお手軽さを損なう方法でもありますが、大規模なアプリ運用が予想される場合には初めから取っておいた方がよい手法かと思います。
あとこの手法も、一応、Firebaseコンソールからはpushを打ってはいけないという運用ルールが必要と言えますかね。
何か有用な情報がありましたら、コメント頂けたら幸いです。