Skip to content

agentHost: graduate the legacy-settings managed-permissions bridge - #333290

Open
joshspicer wants to merge 3 commits into
mainfrom
joshspicer/graduate-legacy-settings-bridge
Open

agentHost: graduate the legacy-settings managed-permissions bridge#333290
joshspicer wants to merge 3 commits into
mainfrom
joshspicer/graduate-legacy-settings-bridge

Conversation

@joshspicer

@joshspicer joshspicer commented Aug 29, 2026

Copy link
Copy Markdown
Member

Graduates the legacy-settings → managedSettings.permissions bridge from its experimental opt-in to the default enforcement path.

Refs #332011. Bridge shipped in #331415; runtime blocker github/copilot-sdk-internal#243, fixed by github/copilot-agent-runtime#16249.

Why this was gated

The runtime treated any managed rule from any source as activating the global managed policy, so one narrow restriction (a single denied domain, one terminal false rule) turned into session-wide prompting for unmatched shell/read/write/URL/factory requests.

github/copilot-agent-runtime#16249 makes client/session-injected managed permissions non-activating: deny/ask/disableBypassPermissionsMode still bind, but they no longer flip unmatched families to "default ask". Server/MDM layers keep today's activating lockdown. Behavior-only and source-based, so VS Code sends nothing new on the wire.

It also fully covers #243 rather than partially: the runtime split the conflated flag into rules_active (client rules still authoritative) and default_ask_active (external layers only). That satisfies #243's first three acceptance criteria; the fourth is this PR.

Verifying the bundled runtime contains #16249

This needed care, because the bump was reverted and re-landed: #332803 bumped it, #332951 reverted it in full after an unrelated session-restore hang (#332885), and #333198 has since re-landed it. main now pins @github/copilot 1.0.82-0 and @github/copilot-sdk 1.0.13-preview.2.

Verified by tag containment on the runtime merge commit — the only reliable check here:

gh api repos/github/copilot-agent-runtime/compare/<tag>...9caaa2f --jq .status
tag status vs. #16249 merge (9caaa2f) contains fix
cli-1.0.80 diverged no
cli-1.0.81-0 diverged no
cli-1.0.81-10 behind yes (first release with it)
cli-1.0.82-0 (current pin) behind yes

Worth flagging for anyone re-checking this: binary symbol presence is not a valid test. Grepping the 1.0.81-0 runtime for _defaultAskActive — the internal key #16249 introduces — returns a match, but that release does not contain the fix. The string ships ahead of the logic. Version-number ordering is also unsafe, since the -N suffixes are not ordered by merge date. Only tag containment answered this correctly.

The re-bump also retires a second hazard. Under the older pins there were two runtimes on disk, including a 1.0.80 nested under @github/copilot-sdk without the fix, and only the explicit resolveCopilotCliPath() override in copilotAgent.ts guaranteed the fixed one enforced. Now that copilot-sdk@1.0.13-preview.2 depends on @github/copilot@^1.0.82-0, that copy dedupes to the same version, so both the explicit path and ordinary module resolution land on a fixed runtime.

Behaviour for users who set the experimental setting

chat.agentHost.copilot.mapLegacySettingsToManagedSettings has been removed from the settings registry. It no longer appears in Settings, and its value is ignored wherever it still exists on disk.

  • true → no change; now the default.
  • unset → the bridge applies; only administrator-configured restrictions are mapped, and per Add support for making multiple lines to one line #16249 they bind without broadening unrelated families.
  • false → ignored, the bridge applies. A leftover entry in settings.json will read as an unknown setting and can be deleted.

Ignoring an explicit false is deliberate. Every mapping contributes only restrictions, sourced from policy/global enterprise settings, so honoring false as a permanent opt-out would let an ordinary user switch off an administrator-configured deny. The escape hatch remains the underlying legacy settings.

Changes

  • agentHostManagedSettings.ts — drop the gate check; replace the stale "contributing any rule makes the managed policy active" JSDoc with the non-activating semantics; drop the setting from managedPermissionsConfigurationIds; document the constant as a deprecated no-op.
  • chat.shared.contribution.ts — remove the setting registration entirely, so Settings no longer advertises a checkbox whose description claims mapping happens "when enabled" while the value does nothing.
  • Tests — remove the inert gate fixture everywhere (including those added by agentHost: map legacy chat.tools.eligibleForAutoApproval to managed settings #333264 and the protocol-boundary forwarding tests); replace the "bridge disabled" test with default-on coverage; keep a guard, using the raw setting id, that a stale settings.json entry cannot switch off a mapped restriction.
  • .github/skills/policy-and-managed-settings/ — the guidance listed the false-by-default gate as a bridge invariant in three places, which would have instructed future work to restore it. Updated.

chat.tools.eligibleForAutoApproval (#333264) landed after this branch and is now default-on too. It's registered policyOnly, so only an enterprise policy value can trigger it — no user preference can lock bypass mode by default.

Not changed, per the issue: no allow list is contributed, host-side SessionPermissionManager stays (still used by Claude/Codex and remote hosts), and expressiveness-gap mappings remain SDK-side work.

Copilot AI balanced review requested due to automatic review settings August 29, 2026 00:02

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Copilot review overview

Review tier: Balanced
Findings: 3 Low severity

New issues introduced by this change (3)
Severity Finding
Low severity src/​vs/​workbench/​contrib/​chat/​browser/​chat.shared.contribution.ts — The deprecation text says this value is ignored, but the adjacent description still says “When…
Low severity src/​vs/​platform/​agentHost/​common/​agentHostManagedSettings.ts — This semantic update leaves the repository's managed-settings guidance stale:…
Low severity src/​vs/​platform/​agentHost/​test/​common/​agentHostManagedSettings.test.ts — The default-on coverage stops at the resolver, while agentHostProtocolClient.test.ts:1214-1217
What changed in this PR

Graduates the legacy-settings permissions bridge to default enforcement following the runtime fix referenced by #332011.

Changes:

  • Removes the experimental opt-in gate.
  • Deprecates the now-ignored setting.
  • Adds default-on and explicit-false tests.
File Description
agentHostManagedSettings.ts Makes permission mapping unconditional.
chat.shared.contribution.ts Deprecates the compatibility setting.
agentHostManagedSettings.test.ts Updates bridge behavior tests.

💡 Configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment thread src/vs/workbench/contrib/chat/browser/chat.shared.contribution.ts Outdated
Comment thread src/vs/platform/agentHost/common/agentHostManagedSettings.ts Outdated
@joshspicer
joshspicer force-pushed the joshspicer/graduate-legacy-settings-bridge branch from 8d85ef1 to 6ee5415 Compare August 31, 2026 18:09
@joshspicer
joshspicer requested a balanced review from Copilot August 31, 2026 18:11

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Copilot review overview

Review tier: Balanced
Findings: 1 Medium severity · 3 Low severity

New issues introduced by this change (1)
Severity Finding
Medium severity src/​vs/​platform/​agentHost/​test/​common/​agentHostManagedSettings.test.ts — This default-on test only verifies the VS Code DTO. It cannot catch the regression that originally…
Pre-existing issues (3)
Severity Finding
Low severity src/​vs/​platform/​agentHost/​test/​common/​agentHostManagedSettings.test.ts — The default-on coverage stops at the resolver, while agentHostProtocolClient.test.ts:1214-1217View comment
Low severity src/​vs/​platform/​agentHost/​common/​agentHostManagedSettings.ts — This semantic update leaves the repository's managed-settings guidance stale:… View comment
Low severity src/​vs/​workbench/​contrib/​chat/​browser/​chat.shared.contribution.ts — The deprecation text says this value is ignored, but the adjacent description still says “When… View comment
Suppressed comments (1)

src/vs/workbench/contrib/chat/browser/chat.shared.contribution.ts:1617

  • The new deprecation text says the value is ignored, but the adjacent setting description still says mapping happens “When enabled.” Both are displayed as user-facing setting documentation, so existing users now receive contradictory guidance. Update the description to describe the always-on bridge without conditioning it on this boolean.
			markdownDeprecationMessage: nls.localize('chat.agentHost.copilot.mapLegacySettingsToManagedSettings.deprecated', "This setting is no longer used. Supported legacy settings are always mapped to Copilot SDK managed settings, so this value is ignored."),

The bridge from legacy VS Code settings to the Copilot SDK's per-session
managedSettings.permissions shipped behind the experimental opt-in
chat.agentHost.copilot.mapLegacySettingsToManagedSettings because the runtime
treated any managed rule from any source as activating the global managed
policy, so one narrow restriction forced unmatched shell/read/write/URL/factory
requests to prompt.

github/copilot-agent-runtime#16249 makes client/session-injected managed
permissions non-activating, which removes that broadening. The bundled runtime
VS Code spawns contains the fix, so the bridge becomes the default enforcement
path.

The setting is deprecated and its value is now ignored rather than honored as an
opt-out: the mappings only ever contribute administrator-configured
restrictions, so honoring an explicit false would let a user switch off an
enterprise policy.

Also drops the now-inert opt-in fixture from the per-tool auto-approval tests
added in #333264, so no test implies the gate still influences the result.

Refs #332011

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
@joshspicer
joshspicer force-pushed the joshspicer/graduate-legacy-settings-bridge branch from 6ee5415 to 6898071 Compare August 31, 2026 18:22
@joshspicer
joshspicer marked this pull request as ready for review August 31, 2026 18:31
@joshspicer
joshspicer requested a balanced review from Copilot August 31, 2026 18:31

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Copilot review overview

Review tier: Balanced
Findings: 2 Medium severity · 3 Low severity

New issues introduced by this change (1)
Severity Finding
Medium severity src/​vs/​workbench/​contrib/​chat/​browser/​chat.shared.contribution.ts — The setting is now ignored for both true and false, but the Settings UI still says mapping…
Pre-existing issues (4)
Severity Finding
Medium severity src/​vs/​platform/​agentHost/​test/​common/​agentHostManagedSettings.test.ts — This default-on test only verifies the VS Code DTO. It cannot catch the regression that originally… View comment
Low severity src/​vs/​platform/​agentHost/​test/​common/​agentHostManagedSettings.test.ts — The default-on coverage stops at the resolver, while agentHostProtocolClient.test.ts:1214-1217View comment
Low severity src/​vs/​platform/​agentHost/​common/​agentHostManagedSettings.ts — This semantic update leaves the repository's managed-settings guidance stale:… View comment
Low severity src/​vs/​workbench/​contrib/​chat/​browser/​chat.shared.contribution.ts — The deprecation text says this value is ignored, but the adjacent description still says “When… View comment

Comment thread src/vs/workbench/contrib/chat/browser/chat.shared.contribution.ts Outdated
joshspicer and others added 2 commits August 31, 2026 11:39
Follow-up to the gate graduation, from PR review:

- The managed-settings skill guidance still listed the false-by-default
  experimental gate as a bridge invariant, which would instruct future work to
  restore the removed gate. Updated in sdk-runtime-policy.md, and in the two
  further places carrying the same claim (legacy-permission-policy.md and
  SKILL.md).
- The protocol-boundary tests still supplied the deprecated opt-in to their
  forwarding fixtures, so they did not prove a local connection forwards
  restrictions without it. Removed, along with the now-unused import.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
The bridge is now unconditional, so the gating setting had no effect while
still presenting a checkbox in Settings whose description claimed mapping
happens "when enabled". A user with an existing `false` value was told the
bridge was disabled while restrictions were in fact enforced.

Remove the setting from the configuration registry and drop the now-unused
constant. The resolver already ignores the value, so behaviour is unchanged;
this only stops Settings from advertising a control that does nothing.

The unit test keeps the regression guard using the raw setting id, so a stale
settings.json entry still cannot switch off an administrator restriction.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
@joshspicer
joshspicer enabled auto-merge (squash) August 31, 2026 18:59
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