Hacktoberfest 2026:维护者为十月标记出来的 issue,仍然开放、适合新手。 浏览 Hacktoberfest issue

[Bug] Unable to Fetch Updated Data from Firebase Remote Config without Restart

未关闭
#1,630 1 条评论 0 个 reaction 已指派 0 人 在 GitHub 查看

还没有人认领这个 Issue。

评估

难度
3/5
预计耗时
1-2 天
新手友好度
35/100
Issue 类型
缺陷
描述清晰度
基本清楚
活跃度
停滞
技术栈
cpp, firebase
领域
cloud

调研方向

从 Firebase C++ quickstart remote_config/testapp 和报告中所示的修改后的 common_main.cc 开始。将 minimum_fetch_interval_in_milliseconds 设置为 0,运行复现步骤,调用 Fetch(0),更改控制台中的值,并比较重复调用 Fetch 和 Activate 的结果。在不重启应用程序的情况下返回更新后的 Remote Config 数据,即表示完成。

由索引模型根据 Issue 内容生成。

描述

api: auth new type: question
[REQUIRED] Please fill in the following fields:
  • Pre-built SDK from the open-source from this repo: https://github.com/firebase/firebase-cpp-sdk/releases/tag/v12.0.0
  • Firebase C++ SDK version: 12.0.0
  • Problematic Firebase Component: Remote Config (Auth, Database, etc.)
  • Other Firebase Components in use: No (Auth, Database, etc.)
  • Platform you are using the C++ SDK on: Mac (Mac, Windows, or Linux)
  • Platform you are targeting: desktop (iOS, Android, and/or desktop)
[REQUIRED] Please describe the issue here:

We are experiencing an issue where our application is unable to fetch updated data from Firebase Remote Config. Despite setting the .minimum_fetch_interval_in_milliseconds to 0 and calling Fetch(0), the application continues to retrieve outdated data until it is restarted.

According to the source code, these steps should be sufficient to fetch the new data immediately. However, changes made to the Firebase Remote Config are not reflected in the app until a restart is performed.

In the attached example (a modified example from https://github.com/firebase/quickstart-cpp/tree/main/remote_config/testapp), I have added 5 attempts to fetch new data with a delay. During the timeout, I change values in the remote config. Below is the output log from the example

Steps to reproduce:
  1. Set up Firebase Remote Config from https://github.com/firebase/quickstart-cpp/tree/main/remote_config/testapp.
  2. Change common_main.cc to provided below or from attached archive.
  3. Set .minimum_fetch_interval_in_milliseconds = 0.
  4. Call Fetch(0) to fetch new data.
  5. Change values in the Firebase Remote Config console.
  6. Attempt to fetch the updated data multiple times with a delay between each attempt.
  7. Observe that the fetched data remains the same (old data) until the application is restarted.

Have you been able to reproduce this issue with just the Firebase C++ quickstarts ?
Yes
What's the issue repro rate? (e g 100%, 1/5 etc)
100%

What happened? How can we make the problem occur?

Initialize the Firebase Remote Config library
Created the Firebase app f3405e80
Try to initialize Firebase RemoteConfig
Initialized the Firebase Remote Config API
Changed ConfigSettings minimum_fetch_interval_in_milliseconds to 0
Fetch...
Fetch Complete
Activate succeeded
Info last_fetch_time_ms=-468513974 (year=2024.60) fetch_status=0 failure_reason=0 throttled_end_time=0
Get test_key "test changed" Remote
GetKeys:
  test_key
Fetch...
Fetch Complete
Activate succeeded
Info last_fetch_time_ms=-468493069 (year=2024.60) fetch_status=0 failure_reason=0 throttled_end_time=0
Get test_key "test changed" Remote
GetKeys:
  test_key
Fetch...
Fetch Complete
Activate succeeded
Info last_fetch_time_ms=-468472180 (year=2024.60) fetch_status=0 failure_reason=0 throttled_end_time=0
Get test_key "test changed" Remote
GetKeys:
  test_key
Relevant Code:
// Copyright 2016 Google Inc. All rights reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include <assert.h>

#include "firebase/app.h"
#include "firebase/remote_config.h"
#include "firebase/util.h"

// Thin OS abstraction layer.
#include "main.h" // NOLINT

using firebase::remote_config::RemoteConfig;

// Convert remote_config::ValueSource to a string.
const char *ValueSourceToString(firebase::remote_config::ValueSource source)
{
  static const char *kSourceToString[] = {
      "Static",  // kValueSourceStaticValue
      "Remote",  // kValueSourceRemoteValue
      "Default", // kValueSourceDefaultValue
  };
  return kSourceToString[source];
}

RemoteConfig *rc_ = nullptr;

// Execute all methods of the C++ Remote Config API.
extern "C" int common_main(int argc, const char *argv[])
{
  namespace remote_config = ::firebase::remote_config;
  ::firebase::App *app;

  // Initialization

  firebase::AppOptions options;
  // Fill options
  // options.set_api_key("");
  // options.set_app_id("");
  // options.set_project_id("");
  // options.set_storage_bucket("");
  // options.set_messaging_sender_id("");

  LogMessage("Initialize the Firebase Remote Config library");
#if defined(__ANDROID__)
  app = ::firebase::App::Create(GetJniEnv(), GetActivity());
#else
  app = ::firebase::App::Create(options);
#endif // defined(__ANDROID__)

  LogMessage("Created the Firebase app %x",
             static_cast<int>(reinterpret_cast<intptr_t>(app)));

  ::firebase::ModuleInitializer initializer;

  void *ptr = nullptr;
  ptr = &rc_;
  initializer.Initialize(app, ptr, [](::firebase::App *app, void *target)
                         {
    LogMessage("Try to initialize Firebase RemoteConfig");
    RemoteConfig **rc_ptr = reinterpret_cast<RemoteConfig **>(target);
    *rc_ptr = RemoteConfig::GetInstance(app);
    return firebase::kInitResultSuccess; });

  while (initializer.InitializeLastResult().status() !=
         firebase::kFutureStatusComplete)
  {
    if (ProcessEvents(100))
      return 1; // exit if requested
  }

  if (initializer.InitializeLastResult().error() != 0)
  {
    LogMessage("Failed to initialize Firebase Remote Config: %s",
               initializer.InitializeLastResult().error_message());
    ProcessEvents(2000);
    return 1;
  }

  LogMessage("Initialized the Firebase Remote Config API");

  auto config_settings_result = rc_->SetConfigSettings(
      {.fetch_timeout_in_milliseconds =
           firebase::remote_config::kDefaultTimeoutInMilliseconds,
       .minimum_fetch_interval_in_milliseconds = 0});

  while (config_settings_result.status() == firebase::kFutureStatusPending)
  {
    if (ProcessEvents(1000))
    {
      break;
    }
  }

  LogMessage("Changed ConfigSettings minimum_fetch_interval_in_milliseconds to 0");

  auto tryWithDelay = [&]()
  {
    // Test Fetch...
    LogMessage("Fetch...");
    auto future_result = rc_->Fetch(0);
    while (future_result.status() == firebase::kFutureStatusPending)
    {
      if (ProcessEvents(1000))
      {
        break;
      }
    }

    if (future_result.status() == firebase::kFutureStatusComplete)
    {
      LogMessage("Fetch Complete");
      auto activate_future_result = rc_->Activate();
      while (future_result.status() == firebase::kFutureStatusPending)
      {
        if (ProcessEvents(1000))
        {
          break;
        }
      }

      bool activate_result = activate_future_result.result();
      LogMessage("Activate %s", activate_result ? "succeeded" : "failed");

      const remote_config::ConfigInfo &info = rc_->GetInfo();
      LogMessage("Info last_fetch_time_ms=%d (year=%.2f) fetch_status=%d "
                 "failure_reason=%d throttled_end_time=%d",
                 static_cast<int>(info.fetch_time),
                 1970.0f + static_cast<float>(info.fetch_time) /
                               (1000.0f * 60.0f * 60.0f * 24.0f * 365.0f),
                 info.last_fetch_status, info.last_fetch_failure_reason,
                 info.throttled_end_time);

      remote_config::ValueInfo value_info;
      std::string result = rc_->GetString("test_key", &value_info);
      LogMessage("Get test_key \"%s\" %s", result.c_str(),
                 ValueSourceToString(value_info.source));

      {
        // Print out the keys that are now tied to data
        std::vector<std::string> keys = rc_->GetKeys();
        LogMessage("GetKeys:");
        for (auto s = keys.begin(); s != keys.end(); ++s)
        {
          LogMessage("  %s", s->c_str());
        }
      }
    }
    else
    {
      LogMessage("Fetch Incomplete");
    }
    // Release a handle to the future so we can shutdown the Remote Config API
    // when exiting the app.  Alternatively we could have placed future_result
    // in a scope different to our shutdown code below.
    future_result.Release();
  };

  for (int i = 5; i > 0; --i)
  {
    tryWithDelay();
    ProcessEvents(20000);
  }

  // Wait until the user wants to quit the app.
  while (!ProcessEvents(1000))
  {
  }

  delete rc_;
  rc_ = nullptr;
  delete app;

  return 0;
}

quickstart-cpp-main.zip

主要语言
C++
星标
326
派生
138
平均合并
2 天 16 小时
30 天内合并 PR
3

贡献指南

打开贡献指南

从这里开始

  1. 先读完整个 Issue,再读项目的贡献指南。
  2. 在 Issue 下留言说明你要接手 —— 这能避免两个人做同样的事。
  3. Fork 仓库,在一个分支上完成修改。
  4. 提交 Pull Request,并在描述里引用这个 Issue 编号。

firebase/firebase-cpp-sdk 的其他 Issue

查看 firebase/firebase-cpp-sdk 的全部 Issue

相似的 Issue

更多 C++ Issue

把新 issue 发到你的邮箱

精选适合新手参与的 GitHub issue 摘要。