Join us for Firebase Summit on November 10, 2021. Tune in to learn how Firebase can help you accelerate app development, release with confidence, and scale with ease. Register

Распространение обновлений Remote Config в режиме реального времени

Использование пульта дистанционного Config фоновую функцию триггеринга обеспечивает облако функции для Firebase вместе с ТСМ , вы можете распространять Удаленная настройка обновлений в режиме реального времени. В этом сценарии вы создаете функцию, которая запускается при публикации или откате шаблона Remote Config с панели управления или API. Обновление шаблона запускает функцию для отправки сообщения FCM, чтобы клиенты знали, что их существующая конфигурация устарела и что их следующая выборка должна быть с сервера:

Остальная часть этого документа проведет вас через эти шаги для распространения обновлений Remote Config в реальном времени.

Подписка экземпляров клиентского приложения на тему FCM

Для нацеливания сообщения FCM на большую группу экземпляров клиентского приложения, такую ​​как вся ваша пользовательская база, обмен тематическими сообщениями является наиболее эффективным механизмом. Каждое приложение экземпляр , который должен получать в реальном времени Удаленные обновления Config должны подписаться на название темы , как, например, PUSH_RC :

Быстрый

extension AppDelegate : MessagingDelegate {
    func messaging(_ messaging: Messaging, didReceiveRegistrationToken fcmToken: String) {
        messaging.subscribe(toTopic: "PUSH_RC") { error in
            print("Subscribed to PUSH_RC topic")
        }
    }
}
    

Цель-C

- (void)messaging:(FIRMessaging *)messaging didReceiveRegistrationToken:(NSString *)fcmToken {
    [[FIRMessaging messaging] subscribeToTopic:@"PUSH_RC" completion:^(NSError * _Nullable error) {
        NSLog(@"Subscribed to PUSH_RC topic");
    }];
}
    

Android

@Override
public void onNewToken(String s) {
    FirebaseMessaging.getInstance().subscribeToTopic("PUSH_RC");
}
    

Создайте функцию для отправки пинга FCM при обновлении шаблона

Вы можете запускать функцию в ответ на события Remote Config, включая публикацию новой версии конфигурации или откат к более старой версии. Чтобы распространять обновления шаблона в реальном времени, создайте функцию, которая прослушивает события публикации шаблона, а затем используйте FCM Admin SDK из своей функции для отправки тихого пинга экземплярам клиентского приложения:

exports.pushConfig = functions.remoteConfig.onUpdate(versionMetadata => {
  // Create FCM payload to send data message to PUSH_RC topic.
  const payload = {
    topic: "PUSH_RC",
    data: {
      "CONFIG_STATE": "STALE"
    }
  };
  // Use the Admin SDK to send the ping via FCM.
  return admin.messaging().send(payload).then(resp => {
    console.log(resp);
    return null;
  });
});

Эта функция устанавливает CONFIG_STATE параметр, а затем посылает его в качестве полезной нагрузки данных сообщени ТСМ всем клиентам подписались на PUSH_RC тему.

Установите состояние удаленной конфигурации на клиенте

Полезная нагрузка Данные , показанная на предыдущем шаге всегда устанавливает CONFIG_STATE в STALE в общих настройках приложения. Это указывает на то, что шаблон удаленной конфигурации, уже сохраненный в приложении, теперь устарел из-за создания нового, обновленного шаблона, публикация которого вызвала запуск функции. Обновите обработчик уведомлений, чтобы проверить это условие:

Быстрый

func application(_ application: UIApplication, didReceiveRemoteNotification userInfo: [AnyHashable: Any],
                 fetchCompletionHandler completionHandler: @escaping (UIBackgroundFetchResult) -> Void) {

    if (userInfo.index(forKey: "CONFIG_STATE") != nil) {
        print("Config set to stale")
        UserDefaults.standard.set(true, forKey:"CONFIG_STALE")
    }

    completionHandler(UIBackgroundFetchResult.newData)
}
    

Цель-C

- (void)application:(UIApplication *)application didReceiveRemoteNotification:(NSDictionary *)userInfo
fetchCompletionHandler:(void (^)(UIBackgroundFetchResult))completionHandler {

    if (userInfo[@"CONFIG_STATE"]) {
        NSLog(@"Config set to stale");
        [[NSUserDefaults standardUserDefaults] setBool:YES forKey:@"CONFIG_STALE"];
    }

    completionHandler(UIBackgroundFetchResultNewData);
}
    

Android

@Override
public void onMessageReceived(RemoteMessage remoteMessage) {
    if (remoteMessage.getData().containsKey("CONFIG_STATE")) {
        SharedPreferences sharedPreferences = PreferenceManager.getDefaultSharedPreferences(this);
        sharedPreferences.edit().putBoolean("CONFIG_STALE", true).apply();
    }
}
    

Получение обновлений Remote Config при запуске приложения

Быстрый

func fetchConfig() {
  welcomeLabel.text = remoteConfig[loadingPhraseConfigKey].stringValue

  var expirationDuration = 3600
  // If your app is using developer mode, expirationDuration is set to 0, so each fetch will
  // retrieve values from the service.
  if remoteConfig.configSettings.isDeveloperModeEnabled || UserDefaults.standard.bool(forKey: "CONFIG_STALE") {
    expirationDuration = 0
  }

  remoteConfig.fetch(withExpirationDuration: TimeInterval(expirationDuration)) { (status, error) -> Void in
    if status == .success {
      print("Config fetched!")
      self.remoteConfig.activateFetched()
    } else {
      print("Config not fetched")
      print("Error: \(error?.localizedDescription ?? "No error available.")")
    }
    self.displayWelcome()
  }
}
    

Цель-C

- (void)fetchConfig {
    self.welcomeLabel.text = self.remoteConfig[kLoadingPhraseConfigKey].stringValue;

    long expirationDuration = 3600;
    // If your app is using developer mode, expirationDuration is set to 0, so each fetch will
    // retrieve values from the Remote Config service.
    if (self.remoteConfig.configSettings.isDeveloperModeEnabled || [[NSUserDefaults standardUserDefaults] boolForKey:@"CONFIG_STALE"]) {
        expirationDuration = 0;
    }

    [self.remoteConfig fetchWithExpirationDuration:expirationDuration completionHandler:^(FIRRemoteConfigFetchStatus status, NSError *error) {
        if (status == FIRRemoteConfigFetchStatusSuccess) {
            NSLog(@"Config fetched!");
            [self.remoteConfig activateFetched];
            [[NSUserDefaults standardUserDefaults] setBool:NO forKey:@"CONFIG_STALE"];
        } else {
            NSLog(@"Config not fetched");
            NSLog(@"Error %@", error.localizedDescription);
        }
        [self displayWelcome];
    }];
}
    

Android

private void fetchWelcomeMessage() {
    mWelcomeTextView.setText(mFirebaseRemoteConfig.getString("loading_phrase"));

    long cacheExpiration = 43200; // 12 hours in seconds.
    // If your app is using developer mode or cache is stale, cacheExpiration is set to 0,
    // so each fetch will retrieve values from the service.
    if (mFirebaseRemoteConfig.getInfo().getConfigSettings().isDeveloperModeEnabled() ||
            mSharedPreferences.getBoolean("CONFIG_STALE", false)) {
        cacheExpiration = 0;
    }

    mFirebaseRemoteConfig.fetch(cacheExpiration)
            .addOnCompleteListener(this, new OnCompleteListener<Void>() {
                @Override
                public void onComplete(@NonNull Task<Void> task) {
                    if (task.isSuccessful()) {
                        Toast.makeText(MainActivity.this, "Fetch Succeeded",
                                Toast.LENGTH_SHORT).show();

                        // After config data is successfully fetched, it must be activated before newly fetched
                        // values are returned.
                        mFirebaseRemoteConfig.activateFetched();
                    } else {
                        Toast.makeText(MainActivity.this, "Fetch Failed",
                                Toast.LENGTH_SHORT).show();
                    }
                    mWelcomeTextView.setText(mFirebaseRemoteConfig.getString("welcome_message"));
                }
            });
}
    

И, наконец, добавить логику вашего приложения , чтобы заставить Удаленная настройка выборки из сети (без учета локального хранилища) , потому что CONFIG_STATE является STALE . Если ваше приложение слишком часто загружается из сети, это может быть ограничено Firebase. См дросселирования .