基本はAndroid端末で、FCM経由でAWSSNSを受け取るまでをなぞった時の奮闘記です。感謝。
バージョンは、 Android 7.0、 API 24。
Push 通知はエミュレータでできるか心配だったけど、この記事の範囲内では問題なかった。
読んでて疑問だったこと (解決はしてない)
- Android package nameにSNSをアプリのパッケージ名を入力する
SNS 関係なさそう
- push Platform NotificationでGoogle Cloud Messaging(GCM)を選択する
- API Keyにコピーした「Legacy server key」を貼り付け、Create platform applicationをクリックする
なんで Legacy なんやろ... なんで GCM なんやろ...
build すると xml でエラー出ちゃう
サンプルなどにある、下記の XML を Manifest.xml に追加するとビルド時にエラーが出ちゃってとっても困った。
<service android:name=".MyFirebaseMessagingService">
<intent-filter>
<action android:name="com.google.firebase.MESSAGING_EVENT"/>
</intent-filter>
</service>
結論としては、自分は階層を間違えていて、正解は application の中の層に書く。
<manifest ... >
<application ... >
......
+ <service android:name=".MyFirebaseMessagingService">
+ <intent-filter>
+ <action android:name="com.google.firebase.MESSAGING_EVENT"/>
+ </intent-filter>
+ </service>
</application>
<uses-permission android:name="android.permission.INTERNET" />
</manifest>
まあ考えれば当たり前なんですけど、手探りで作業して全体像がボヤーっとしてると間違えたままになっちゃったりとか、ありません?
ちなみに端折ったんでしけど、 service はトークン取得のためにもう一個書いている。
エミュレータでFirebase の token 取れない
何やらエラーが出るので、 firebase のトークン取得を下記のように書いていたら、 token is null
だった。
String token = FirebaseInstanceId.getInstance().getToken();
if (token == null) {
Log.d(TAG, "token is null.");
} else {
sendRegistrationToServer(token);
}
エミュレータがインターネッツに繋がってない場合があるので、再起動すると治った
https://stackoverflow.com/questions/37517860/how-to-handle-firebaseinstanceid-getinstance-gettoken-null
適当なところで onTokenRefresh を呼び出してもエラーで落ちる
onRefreshToken がどのタイミングで呼ばれるかよく分からなかっため、起動時に通過する Activityから強制的に呼び出してみました。エラーが出たので } catch (Exception ex) {
したら、 ex.getMessage()
には何も入ってなかったんですが、 ex.getClass()
すると NetworkOnMainThreadException
が出てきました。これはなんか聞いたことがあったなと思って調べたら、「メインスレッドで HTTP 通信するな」っていうやつです。つまるところ、自分の場合は「適当なところで」というのが適当すぎて不適切でした。
public class MyFirebaseSnsRegistrationService extends AsyncTask<String, Void, String> {
@Override
protected String doInBackground(String... params) {
MyFirebaseInstanceIdService service = new MyFirebaseInstanceIdService();
service.onTokenRefresh();
return "";
}
}
こんな非同期クラスを書いて、これを Activity から呼び出してやると、SNS への同期が完了しました。
メッセージの受け取りはまだ実装していないのですが、 SNS のコンソールからテストメッセージを送信してみたところ、無事ログには FCM からのメッセージの受信が出ました。流れは理解できたような気がします。