| name | mobile-feature-flags |
|---|---|
| description | Feature flag management with PostHog, LaunchDarkly, or Firebase Remote Config for React Native/Expo and Flutter |
| standards-version | 1.9.0 |
Use this skill when the developer asks about:
- Feature flags, feature toggles, or feature switches
- A/B testing or experimentation frameworks
- Staged rollouts or percentage-based releases
- Kill switches for disabling features remotely
- PostHog, LaunchDarkly, or Firebase Remote Config integration
- Typed flag definitions with default values
- User targeting or segmentation for features
| Input | Description |
|---|---|
| Framework | expo (React Native) or flutter |
| Provider | posthog, launchdarkly, or firebase |
Run mobile_setupFeatureFlags to generate the typed provider:
Use MCP tool: mobile_setupFeatureFlags
framework: "expo"
provider: "posthog"
output_directory: "lib"
This creates a feature-flags.ts (or .dart) file with:
- Typed flag enum/interface with default values
- Provider initialization
getFlag()/useFeatureFlag()helpers- User identification for targeting
import { useFeatureFlag, identifyUser } from "@/lib/feature-flags";
// After auth
identifyUser(user.id, { plan: user.plan, region: user.region });
// In components
function SettingsScreen() {
const showNewOnboarding = useFeatureFlag("new_onboarding");
return showNewOnboarding ? <NewOnboarding /> : <LegacyOnboarding />;
}import { initFeatureFlags, getFlag, onFlagChange } from "@/lib/feature-flags";
await initFeatureFlags(user.id);
const isPremium = getFlag("premium_features");
const unsubscribe = onFlagChange("premium_features", (value) => {
console.log("Flag changed:", value);
});import { initFeatureFlags, getFlag, refreshFlags } from "@/lib/feature-flags";
await initFeatureFlags();
const showExperimental = getFlag("experimental_ui");
// Refresh on app foreground
useEffect(() => {
const sub = AppState.addEventListener("change", (state) => {
if (state === "active") refreshFlags();
});
return () => sub.remove();
}, []);final flags = FeatureFlagService();
await flags.init();
if (flags.isEnabled(FeatureFlag.newOnboarding)) {
// Show new flow
} else {
// Show legacy flow
}
// Debug overrides (dev builds only)
if (kDebugMode) {
flags.setOverride(FeatureFlag.experimentalUi, true);
}- Add to the
FeatureFlagstype/enum with a safe default (usuallyfalse) - Create the flag in your provider dashboard
- Use the flag in code
- Set targeting rules in the dashboard
- Remove the flag after full rollout
| Stage | % of Users | Duration | Criteria |
|---|---|---|---|
| Internal | 0% (staff only) | 1 week | Employee targeting |
| Canary | 5% | 3 days | Monitor crash rates |
| Beta | 25% | 1 week | Monitor metrics |
| GA | 100% | - | Remove flag |
const isFeatureDisabled = useFeatureFlag("kill_switch_payments");
if (isFeatureDisabled) {
return <MaintenanceScreen />;
}| Resource | URL |
|---|---|
| PostHog React Native | https://posthog.com/docs/libraries/react-native |
| LaunchDarkly React Native | https://docs.launchdarkly.com/sdk/client-side/react-native |
| Firebase Remote Config | https://firebase.google.com/docs/remote-config |
| PostHog Feature Flags | https://posthog.com/docs/feature-flags |
User: "Set up feature flags with PostHog so I can do staged rollouts"
Assistant:
- Runs
mobile_setupFeatureFlagswithprovider: "posthog"to generate typed flag module - Runs
mobile_installDependencyto installposthog-react-native - Shows how to add
EXPO_PUBLIC_POSTHOG_KEYto.env - Demonstrates
useFeatureFlag("new_onboarding")in a component - Explains staged rollout process: internal → 5% canary → 25% beta → 100% GA
- Shows how to call
identifyUser()after authentication for user targeting
| Tool | When |
|---|---|
mobile_setupFeatureFlags |
Generate the typed feature flag module |
mobile_installDependency |
Install the provider SDK package |
- No default values - always define a safe fallback; network requests can fail.
- Stale flags - refresh on app foreground, not just on launch.
- Flag debt - remove flags after full rollout; stale flags accumulate complexity.
- Testing without flags - unit tests should mock flag values for both branches.
- Targeting before identification - call
identify()before reading user-targeted flags. - Boolean-only flags - some providers support string/JSON flags for multivariate tests.
mobile-analytics- track flag impressions and conversion eventsmobile-ci-cd- CI checks that verify flag defaults match expectationsmobile-ota-updates- combine flags with OTA channels for staged releases