Как запустить службу идентификации FCM только после запуска определенного действия?
Предположим, у меня есть LoginActivity
, где пользователь может либо зарегистрироваться, либо войти в систему с существующими учетными данными. Я не хочу, чтобы FirebaseInstanceIdService
генерировал токен, если пользователь не вошел в систему, и MainActivity
приложения не запущено.
Спасибо
Ответы
Ответ 1
Вы не можете заблокировать FirebaseInstanceIdService.onTokenRefresh()
от вызова до тех пор, пока пользователь не войдет в систему.
Что вы можете сделать в своем случае:
- В
FirebaseInstanceIdService.onTokenRefresh()
игнорировать событие, если пользователь не вошел в систему
- Когда пользователь выполнит вход в систему
FirebaseInstanceId.getToken()
и != null
вызовет onTokenRefresh()
(или непосредственно вашу логику) вручную.
Таким образом вы можете обработать токен, когда пользователь выполнил вход в систему, и если токен недоступен (или повернут), вы позже получите событие onTokenRefresh()
.
Обновление (3 июля 2017 г.). В комментариях читатель напомнил, что FirebaseInstanceIdService.onTokenRefresh()
можно вызвать после входа пользователя в систему.
Это правильно. Когда пользователь входит в систему, getToken()
все равно может вернуться null
, если onTokenRefresh()
не был вызван ранее.
Вам нужно использовать этот случай в своем приложении. Скорее всего, пользователь может использовать приложение в любом случае, но вы не можете отправить push-уведомление, пока не получите токен.
Когда onTokenRefresh()
наконец-то вызывается, если пользователь регистрируется раньше, чем вы можете связать токен с пользователем.
Ответ 2
Извините, но это невозможно. FirebaseInstanceIdService
автоматически запускается при запуске приложения и генерирует Token
. Имейте в виду, что это связано с приложением Instance
. Не с одним конкретным пользователем. Если вы пытаетесь сохранить Token
с одним конкретным пользователем (т.е. Когда пользователь выполнил вход в систему, вы сохраните его Token
на сервере db для push-уведомления этого пользователя). Если вы делаете это, вы столкнетесь в будущем заключается в том, что если два пользователя используют одно приложение Instance
, то push-уведомление может быть перенаправлено неверному пользователю.
Надеюсь, вы поняли мою мысль.
Ответ 3
Я поддерживаю один флаг в shared pref, который указывает, отправлен ли gcm-маркер на сервер или нет. В окне Splash каждый раз, когда я вызываю один метод sendDevicetokenToServer. Этот метод проверяет, не является ли идентификатор пользователя пустым и gcm отправить статус, а затем отправить токен на сервер.
public static void sendRegistrationToServer(final Context context) {
if(Common.getBooleanPerf(context,Constants.isTokenSentToServer,false) ||
Common.getStringPref(context,Constants.userId,"").isEmpty()){
return;
}
String token = FirebaseInstanceId.getInstance().getToken();
String userId = Common.getUserId(context);
if(!userId.isEmpty()) {
HashMap<String, Object> reqJson = new HashMap<>();
reqJson.put("deviceToken", token);
ApiInterface apiService =
ApiClient.getClient().create(ApiInterface.class);
Call<JsonElement> call = apiService.updateDeviceToken(reqJson,Common.getUserId(context),Common.getAccessToken(context));
call.enqueue(new Callback<JsonElement>() {
@Override
public void onResponse(Call<JsonElement> call, Response<JsonElement> serverResponse) {
try {
JsonElement jsonElement = serverResponse.body();
JSONObject response = new JSONObject(jsonElement.toString());
if(context == null ){
return;
}
if(response.getString(Constants.statusCode).equalsIgnoreCase(Constants.responseStatusSuccess)) {
Common.saveBooleanPref(context,Constants.isTokenSentToServer,true);
}
}catch (Exception e){
e.printStackTrace();
}
}
@Override
public void onFailure(Call<JsonElement> call, Throwable throwable) {
Log.d("", "RetroFit2.0 :getAppVersion: " + "eroorrrrrrrrrrrr");
Log.e("eroooooooorr", throwable.toString());
}
});
}
}
В классе MyFirebaseInstanceIDService
@Override
public void onTokenRefresh() {
// Get updated InstanceID token.
String refreshedToken = FirebaseInstanceId.getInstance().getToken();
Log.d(TAG, "Refreshed token: " + refreshedToken);
// If you want to send messages to this application instance or
// manage this apps subscriptions on the server side, send the
// Instance ID token to your app server.
Common.saveBooleanPref(this,Constants.isTokenSentToServer,false);
Common.sendRegistrationToServer(this);
}