feat: open useful USER_TYPE-gated features to all users (#644)

* feat: open useful USER_TYPE-gated features to all users

Remove 13 process.env.USER_TYPE === 'ant' gates that restricted useful
features to Anthropic employees. These features work without Anthropic
infrastructure and are now available to all open-build users.

Features opened:
- Agent nesting (sub-agents can spawn sub-agents)
- Effort 'max' persistence in settings
- Plan mode interview phase (controlled by feature flags)
- Sandbox disabled commands (via ~/.claude/feature-flags.json)
- All tips visible to all users (plan mode, feedback, shift-tab)

Simplified:
- Fullscreen defaults to off (use /config to enable)
- Explore agent always uses haiku model
- Plan mode tool uses conservative prompt for all users

Continues the USER_TYPE cleanup from #637 (dead code) and builds
on #639 (local feature flags).

* fix: address Copilot review comments — remove residual dead code

1. bridgeConfig.ts: ungate bridge override functions — return env vars
   directly instead of hardcoded undefined
2. bridgeMain.ts + initReplBridge.ts: ungate sessionIngressUrl — read
   CLAUDE_BRIDGE_SESSION_INGRESS_URL without USER_TYPE check
3. tools.ts: remove dead ConfigTool/TungstenTool imports, narrow
   eslint-disable scope, stub REPLTool/SuggestBackgroundPRTool to null
4. readOnlyValidation.ts: remove orphaned ANT_ONLY_COMMAND_ALLOWLIST
   and unused GH_READ_ONLY_COMMANDS import
5. insights.ts: remove entire remote collection plumbing (types,
   functions, options, display logic)
6. osc.ts: hardcode supportsTabStatus() to false (internal-only feature)
7. state.ts: simplify addSlowOperation/getSlowOperations to no-ops,
   remove dead constants

* fix: address Copilot review on PR #644

1. settings/types.ts: allow 'max' effort level for all users in Zod
   schema — was still gated behind USER_TYPE=ant, causing 'max' to be
   silently dropped on settings reload
2. shouldUseSandbox.ts: defensively normalize disabledCommands from
   feature flag config with Array.isArray() guards

* fix: address second round of Copilot review on PR #644

1. shouldUseSandbox.ts: validate top-level shape of disabledCommands
   before accessing properties (handles null/primitive from feature flag)
2. fullscreen.ts: update JSDoc to reflect removal of USER_TYPE default
3. osc.ts: update JSDoc — "Ant-only" → "Currently disabled"
This commit is contained in:
Nourrisse Florian
2026-04-14 13:08:54 +02:00
committed by GitHub
parent 658d076909
commit c1beea9867
17 changed files with 75 additions and 539 deletions

View File

@@ -109,7 +109,6 @@ const externalTips: Tip[] = [
`Use Plan Mode to prepare for a complex request before making changes. Press ${getShortcutDisplay('chat:cycleMode', 'Chat', 'shift+tab')} twice to enable.`,
cooldownSessions: 5,
isRelevant: async () => {
if (process.env.USER_TYPE === 'ant') return false
const config = getGlobalConfig()
// Show to users who haven't used plan mode recently (7+ days)
const daysSinceLastUse = config.lastPlanModeUse
@@ -401,9 +400,7 @@ const externalTips: Tip[] = [
{
id: 'shift-tab',
content: async () =>
process.env.USER_TYPE === 'ant'
? `Hit ${getShortcutDisplay('chat:cycleMode', 'Chat', 'shift+tab')} to cycle between default mode and auto mode`
: `Hit ${getShortcutDisplay('chat:cycleMode', 'Chat', 'shift+tab')} to cycle between default mode, auto-accept edit mode, and plan mode`,
`Hit ${getShortcutDisplay('chat:cycleMode', 'Chat', 'shift+tab')} to cycle between default mode, auto-accept edit mode, and plan mode`,
cooldownSessions: 10,
isRelevant: async () => true,
},
@@ -476,7 +473,6 @@ const externalTips: Tip[] = [
`Your default model setting is Opus Plan Mode. Press ${getShortcutDisplay('chat:cycleMode', 'Chat', 'shift+tab')} twice to activate Plan Mode and plan with Claude Opus.`,
cooldownSessions: 2,
async isRelevant() {
if (process.env.USER_TYPE === 'ant') return false
const config = getGlobalConfig()
const modelSetting = getUserSpecifiedModelSetting()
const hasOpusPlanMode = modelSetting === 'opusplan'
@@ -624,33 +620,12 @@ const externalTips: Tip[] = [
content: async () => 'Use /feedback to help us improve!',
cooldownSessions: 15,
async isRelevant() {
if (process.env.USER_TYPE === 'ant') {
return false
}
const config = getGlobalConfig()
return config.numStartups > 5
},
},
]
const internalOnlyTips: Tip[] =
process.env.USER_TYPE === 'ant'
? [
{
id: 'important-claudemd',
content: async () =>
'[internal] Use "IMPORTANT:" prefix for must-follow CLAUDE.md rules',
cooldownSessions: 30,
isRelevant: async () => true,
},
{
id: 'skillify',
content: async () =>
'[internal] Use /skillify to turn repeatable recurring workflows into reusable project skills',
cooldownSessions: 15,
isRelevant: async () => true,
},
]
: []
const internalOnlyTips: Tip[] = []
function getCustomTips(): Tip[] {
const settings = getInitialSettings()