Repository navigation
fix(flags): respect feature enrollment in local evaluation - #1176
Conversation
A flag with early access feature enrollment now uses the $feature_enrollment/<flag key> person property when it is passed, like the flags service. Without it, local evaluation is inconclusive (missing_context) and falls back to /flags, instead of returning a certain False for enrolled people. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Generated-By: PostHog Desktop Task-Id: fecca688-37ac-44b6-a1b5-27e11cb0749b
There was a problem hiding this comment.
PostHog Review · Standard · reviewed dbfb25f: 1 Should fix.
This is the only automatic review while this pull request is a draft. Comment @posthog review to review new changes sooner. Otherwise, a review of the new changes runs when you mark it ready for review.
See this review and its findings in PostHog Review. Comment @posthog review --deep for a Deep review. A Deep review takes longer and looks deeper than a Standard review.
| return ( | ||
| properties[enrollment_key] is True or properties[enrollment_key] == "true" | ||
| ) |
There was a problem hiding this comment.
P2 · Read enrollment from person properties for group-scoped flags
For group-scoped enrollment flags, _compute_flag_locally passes group properties as properties. This return therefore treats a group's enrollment value as the person's, producing True even when the person explicitly opted out. The flags service always reads person properties for enrollment; preserve person context separately for this check.
There was a problem hiding this comment.
Fixed in fffef4d. A group flag with feature enrollment is now unresolved locally and falls back to /flags, because the flags service reads enrollment from the person. The enrollment test covers a group that says enrolled and a person who opted out.
posthog-python Compliance ReportDate: 2026-11-04T13:37:41.923636+00:00 ✅ All Tests Passed!121/121 tests passed Capture_V1 Tests✅ 95/95 tests passed View Details
Capture_Ai Tests✅ 5/5 tests passed View Details
Feature_Flags Tests✅ 17/17 tests passed View Details
Feature_Flags_Local_Evaluation Tests✅ 4/4 tests passed View Details
|
Check enrollment only when feature_enrollment is boolean true, and treat only true or "true" as enrolled, like the flags service. A value such as 1 now reads as opted out instead of enrolled. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Generated-By: PostHog Desktop Task-Id: fecca688-37ac-44b6-a1b5-27e11cb0749b
…vice For a group flag, local evaluation passes group properties, but the flags service reads enrollment from the person. Local evaluation now treats a group flag with feature enrollment as unresolved, so it falls back to /flags. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Generated-By: PostHog Desktop Task-Id: fecca688-37ac-44b6-a1b5-27e11cb0749b
💡 Motivation and Context
Local evaluation ignores early access enrollment (
filters.feature_enrollment). A person who turned on a feature in Feature previews, but matches no release condition, getsFalseon the server andTruein posthog-js.Example: the browser shows a beta page, and its API (gated with
feature_enabled()) refuses every call.This PR applies the flags service rule: the enrollment property decides first.
flowchart LR A{"feature_enrollment"} -->|"off"| C["release conditions"] A -->|"on"| B{"property passed?"} B -->|"yes"| D["true or 'true' = enrolled"] B -->|"no"| E["/flags"] classDef blue fill:#1d4aff,stroke:#1d4aff,color:#fff; classDef red fill:#f54e00,stroke:#f54e00,color:#fff; classDef gray fill:#e5e7eb,stroke:#c7ccd1,color:#000; class A,B blue; class E red; class C,D gray;$feature_enrollment/<key>False❌/flags"true"False❌True, localFalseTrue❌False, local1True❌False, local/flagsWhy this is correct
trueor"true"means enrolled, and any other value means opted out.missing_contextis the existing reason for "pass this property to evaluate locally".Trade-off: an enrollment flag now calls
/flagsunless the property is passed, like experience continuity. Withonly_evaluate_locally=True, it is unresolved instead of a wrongFalse.No PostHog SDK handles
feature_enrollmenttoday. posthog-node 5.61.2 has the same gap.💚 How did you test it?
test_feature_enrollment_flagcovers the four table rows, and each row failed before the fix. Not tested against a live flags service.📝 Checklist
If releasing new changes
sampo addto generate a changeset file🤖 Agent context
Autonomy: Human-driven (agent-assisted)
Claude Code, Claude Opus 5.5 (
claude-opus-5-5). Found while debugging PostHog's Today page, where key numbers never loaded for Feature previews users. The app-side workaround is PostHog/posthog#128585.Created with PostHog Desktop from a PostHog Desktop task
🤖 Generated with Claude Code