Skills Visibility via Feature Flags (Gateway-Controlled)#10183
Conversation
* feat: add skill feature flags config and enforcement Co-Authored-By: Claude <noreply@anthropic.com> * fix: enforce feature flags on included child skills and dynamic prompt section Add isSkillFeatureEnabled checks in skill_load for child skills in both the body-loading loop and the loaded_skill marker loop, so flag-OFF child skills are fully hidden. Also filter hardcoded browser/twitter references in buildDynamicSkillWorkflowSection through isSkillFeatureEnabled so the system prompt does not advertise disabled skills. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> --------- Co-authored-by: Claude <noreply@anthropic.com>
* feat: add gateway feature-flags REST API with config persistence Co-Authored-By: Claude <noreply@anthropic.com> * fix: handle malformed URI encoding and config parse errors in feature-flags - Wrap decodeURIComponent in try/catch in gateway/src/index.ts to return 400 Bad Request on malformed percent-encoding instead of crashing to the global error handler with a misleading 500. - Refactor readConfigFile to use a discriminated union result type that distinguishes "file doesn't exist" (returns empty config) from "file exists but can't be parsed" (returns error). The PATCH handler now returns 500 with a descriptive message when the config file is malformed, preventing silent data loss. The GET handler gracefully degrades to empty flags on parse errors (no data loss risk). Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * fix: validate parsed config is a plain object in readConfigFile --------- Co-authored-by: Claude <noreply@anthropic.com>
* feat: add client-only PATCH auth split for feature-flags Co-Authored-By: Claude <noreply@anthropic.com> * fix: remove rate-limit on 403 and handle identical token edge case - Remove authRateLimiter.recordFailure() from 403 path to avoid penalizing legitimately authenticated clients who used the wrong token type (Issue 1) - Only record failures on 401 (truly invalid authentication) - Skip runtime-token rejection when FEATURE_FLAG_TOKEN is identical to runtimeBearerToken to support single-token deployments (Issue 2) Addresses review feedback on PR #10171 --------- Co-authored-by: Claude <noreply@anthropic.com>
* feat: add feature-flag client token plumbing for macOS/iOS Co-Authored-By: Claude <noreply@anthropic.com> * fix: throw on unavailable transport, always use gateway on macOS, clear stale token Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> --------- Co-authored-by: Claude <noreply@anthropic.com>
Co-authored-by: Claude <noreply@anthropic.com>
|
@codex review |
…-pair Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Thorough review findingsI pulled this PR into a local worktree and did a full diff + build/test pass. Findings below are ordered by severity.
Validation run
|
1. [P1] Fix gateway type-check: remove dead `not_found` variant from ConfigReadResult union (fixes narrowing bug on `result.detail`), make `featureFlagToken` optional in GatewayConfig type. 2. [P1] Add featureFlagToken to pairing responses: runtime now reads ~/.vellum/feature-flag-token and includes it in approval responses so iOS receives the token during QR pairing. 3. [P1] Fix PATCH auth bypass when tokens equal: loadConfig() now detects token collision and regenerates the feature-flag token to ensure the auth split is always enforceable. 4. [P2] Gate guardian-verification section on feature flags: system prompt skips buildGuardianVerificationRoutingSection() when guardian-verify-setup skill flag is OFF. 5. [P2] Fix failing integration test: removed incorrect assertion that <available_skills> disappears when only browser/twitter flags are OFF (bundled skills remain visible). 6. [P2] Fix macOS local HTTP transport: setFeatureFlag now checks if httpTransport.baseURL is localhost before delegating — local HTTP mode (localHttpEnabled) falls through to the direct gateway call. 7. [P2] Accept dotted skill IDs in feature-flag keys: updated regex from [a-z0-9_-]+ to [a-z0-9][a-z0-9._-]* to match managed skill ID validation.
|
Addressed all 7 review findings in commit cdcb35d: P1 fixes:
P2 fixes: Validation:
|
…way/resolve-main # Conflicts: # clients/macos/vellum-assistant/Features/MainWindow/PanelCoordinator.swift
|
Addressed remaining review feedback (P2: serialize feature-flag config writes) in #10244 |
Summary
Make skill exposure controllable by feature flags so a WIP skill can be turned off and become unavailable everywhere — hidden from UIs, model prompts, skill_load, and active tool projection.
Changes
featureFlagsconfig section to assistant and enforced at all skill exposure paths (skill list, system prompt, skill_load, tool projection, child skill includes)GET /v1/feature-flagsandPATCH /v1/feature-flags/:flagKeygateway endpoints with workspace config persistence, atomic writes, and key validation~/.vellum/feature-flag-token) distinct from runtime bearer token. PATCH requires client token, explicitly rejects runtime tokensetFeatureFlag()helper for both platformsMilestone PRs (merged into feature branch)
Project issue
Closes #10145
Test plan
skills.<id>.enabled=falsevia PATCH and confirm skill disappears from UI skill list/skillslash for that skill is unknownskill_loadfor that skill failsGenerated with Claude Code