Skip to content

Fix Android flags core lookup#1304

Merged
leoromanovsky merged 1 commit into
developfrom
leo.romanovsky/fix-android-flags-lazy-core
Jun 12, 2026
Merged

Fix Android flags core lookup#1304
leoromanovsky merged 1 commit into
developfrom
leo.romanovsky/fix-android-flags-lazy-core

Conversation

@leoromanovsky

Copy link
Copy Markdown
Contributor

Motivation

Android React Native apps can construct the DdFlags native module while the JavaScript bundle is still evaluating, before DdSdk.initialize has initialized the Datadog SDK. The Android flags implementation captured Datadog.getInstance() in the constructor, so that early construction could pin a no-op core for the lifetime of the process. In that state, enabling Flags had no effect and OpenFeature clients fell back to defaults even after the SDK initialized.

Changes

This PR changes the Android flags implementation to keep test injection support while resolving the Datadog SdkCore lazily when Flags are enabled or a native Flags client is created. That makes the Android path match the intended initialization order for React Native and Expo apps: module construction can happen early, but the core used for Flags comes from the initialized SDK when the app calls DdFlags.enable() and sets up OpenFeature.

A focused Kotlin regression test covers both parts of the failure mode: constructing DdFlagsImplementation no longer calls Datadog.getInstance(), and an implementation constructed while a stale core is current uses the later initialized core when enable() is called.

Decisions

The fix intentionally stays inside the Android native implementation instead of adding JavaScript ordering requirements or Expo-specific setup. The public JS API and OpenFeature provider behavior remain unchanged, and existing tests can still inject an explicit SdkCore override.

Validation: git diff --check passed. I attempted ./gradlew testDebugUnitTest --tests com.datadog.reactnative.DdFlagsImplementationTest; local execution is blocked because this environment has no Android SDK configured (ANDROID_HOME is unset).

@leoromanovsky leoromanovsky marked this pull request as ready for review June 12, 2026 14:00
Copilot AI review requested due to automatic review settings June 12, 2026 14:00
@leoromanovsky leoromanovsky requested a review from a team as a code owner June 12, 2026 14:00
@leoromanovsky leoromanovsky merged commit b5a66ad into develop Jun 12, 2026
12 checks passed
@leoromanovsky leoromanovsky deleted the leo.romanovsky/fix-android-flags-lazy-core branch June 12, 2026 14:01

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR fixes an Android React Native initialization-order issue where DdFlagsImplementation could capture a no-op SdkCore during module construction (before DdSdk.initialize), causing Flags/OpenFeature to remain ineffective for the app lifetime. The implementation now resolves the Datadog core lazily when Flags are enabled or a native Flags client is created, and adds a Kotlin regression test covering the failure mode.

Changes:

  • Update DdFlagsImplementation to lazily resolve Datadog.getInstance() via a getter rather than in the constructor, while still allowing test injection.
  • Add a regression test ensuring construction does not touch Datadog.getInstance() and enable() uses the currently initialized core.

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 1 comment.

File Description
packages/core/android/src/main/kotlin/com/datadog/reactnative/DdFlagsImplementation.kt Switch SdkCore resolution to a lazy getter to avoid pinning a stale/no-op core during early module construction.
packages/core/android/src/test/kotlin/com/datadog/reactnative/DdFlagsImplementationTest.kt Add regression coverage for “no core lookup during construction” and “use current core on enable()”.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines 28 to +35
class DdFlagsImplementation(
private val sdkCore: SdkCore = Datadog.getInstance(),
private val sdkCoreOverride: SdkCore? = null,
) {
private val clients: MutableMap<String, FlagsClient> = mutableMapOf()

private val sdkCore: SdkCore
get() = sdkCoreOverride ?: Datadog.getInstance()

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants