Guides/Playbook

GitHub Copilot managed permissions: Deploy and verify policy

8 min read
On this page
Overlapping permission layers narrow the paths an agent operation can follow

Copilot managed permissions

General Analysis

A policy committed to GitHub can still be absent from the agent session it was meant to constrain. The developer may be using a different billing account, the client may not have refreshed, or the session may use a runtime that does not support the rule. Start a Copilot permissions rollout by proving which policy reached which session.

GitHub made managed operation permissions generally available on September 9, 2026. Copilot Business and Enterprise administrators can govern shell operations, file reads and edits, and network domains in the Copilot app, CLI, and VS Code sessions using Agent Host. The configuration and acceptance checks below follow the documentation; General Analysis has not tested enforcement in a Copilot deployment.

Use How to Secure Coding Agents for the broader rollout baseline.

Record the client and session type first#

Record the client version, operating system, signed-in account, billing enterprise, and session runtime for each pilot group. A row labeled only "VS Code" is too vague for this release.

GitHub's permission reference limits granular rules in VS Code to Agent Host sessions. Disabling bypass mode has broader support. A disabled allow-all button therefore does not establish that a file or command rule works.

On September 10, the VS Code enterprise guide still says granular managed rules are CLI-only, while GitHub's dated announcement and reference include Agent Host. That conflict makes the session type an acceptance requirement: record the exact versions and verify behavior before approving that group. These sources do not establish one minimum version for every client.

JetBrains managed sandbox policies entered public preview on September 8. That is a separate capability. Likewise, a client appearing in the managed-settings client list does not mean it supports every property. Do not extend this release's granular-permission claim to cloud-agent tasks or every IDE session.

See how your AI systems hold up under real attacks

General Analysis maps AI applications and agents, red teams prompts, retrieval, tools, MCP servers, browser actions, permissions, and business workflows, then turns findings into evidence your team can reproduce and retest.

Choose how the policy reaches the user#

Use GitHub's deployment-method guidance to separate account governance from device governance:

DeliveryApplies throughBest reason to choose it
Server-managedThe user's enterprise Copilot licenseReview policy in Git and specialize eligible settings by enterprise team.
Native MDMManaged local devices, independent of license sourceKeep device restrictions when users change accounts or cannot obtain server policy.
Managed fileLocal clients on machines receiving the fileCover environments where repository delivery or native MDM is unsuitable.

The CLI has a documented availability gap: if fetching server settings fails and no cached response exists, that session has no server-managed policy. Put indispensable device restrictions in device delivery. Do not treat a fresh-fetch preference as proof that startup fails closed; the CLI reference says forceRemoteSettingsRefresh retains cached policy as a fallback.

This matters for incident containment. A repository commit records the intended policy change. Until you confirm delivery, use independently enforced account, device, or downstream-service controls for an urgent restriction. Policy refresh is not an immediate revocation guarantee.

Deploy a small policy whose behavior is easy to recognize#

An enterprise owner selects the governance source under AI controls → Agents → Configuration source. The selected organization owns the .github-private repository. GitHub's repository setup guide also explains how to protect that repository with rulesets. Require review of policy edits and team mappings: changing a mapping can change permissions without editing the baseline rule.

Place the policy at copilot/managed-settings.json on that repository's default branch. The getting-started guide ties server delivery to users licensed through the enterprise or its organizations, regardless of their access to the governance repository. For a user with multiple license sources, check Usage billed to in personal Copilot settings.

The following pilot uses a harmless fixture directory. Create files containing dummy text under policy-pilot/; the example does not grant shell or network access. Adapt it to the approved workload before using it as a baseline.

Code source: illustrative configuration using GitHub's managed-permission schema.

JSON
{ "permissions": { "disableBypassPermissionsMode": "disable", "deny": ["Read(/policy-pilot/blocked.txt)"], "ask": ["Edit(/policy-pilot/review.txt)"], "allow": ["Read(/policy-pilot/**)"] } }

In these selectors, / means the workspace root; // means the filesystem root. GitHub specifies deny > ask > allow, and a managed ask needs a new human approval each time. Declaring these rules also makes unmatched supported operations require approval. The pilot's broad read rule deliberately overlaps the denied fixture so you can check precedence without touching a secret.

Use the same harmless fixtures for the acceptance record:

Requested operationExpected decision from this policyWhat to record
Read policy-pilot/allowed.txtAllow, subject to other applicable policyThe operation and decision, including any additional restriction.
Read policy-pilot/blocked.txtDeny, despite the broader read allowanceThe matched denial; a model choosing not to read is insufficient evidence.
Edit policy-pilot/review.txt twiceFresh approval for each editBoth requests, both decisions, and the resulting fixture changes.
Read a dummy file outside policy-pilot/Ask, unless another rule changes the resultThe effective policy sources that explain the decision.

These are proposed administrative acceptance checks, not reported test results. Check the actual tool request: a direct file read and a command that reads a file are different operation paths. Do not assume one observed denial proves filesystem isolation.

Native MDM and managed files have different formats#

Native MDM delivers individual string values, not the JSON file above. Nested keys use dot notation; arrays and booleans become JSON text inside strings. For example, permissions.deny carries ["Read(/policy-pilot/blocked.txt)"] as its string value. Preserve that distinction when preparing the device payload. GitHub documents the native representation and delivery locations.

For file delivery, the CLI paths are /Library/Application Support/GitHubCopilot/managed-settings.json on macOS, %ProgramFiles%\GitHubCopilot\managed-settings.json on Windows, and /etc/github-copilot/managed-settings.json on Linux. On POSIX systems, the CLI reference requires a real, root-owned file and rejects symlinks and world-writable files. Use non-writable permissions for both group and other users, following the stricter delivery guide. A file in a developer's personal configuration directory is not equivalent evidence of managed delivery.

Review team exceptions separately from device policy#

Within server delivery, enterprise team overrides can replace eligible values marked overridable. copilot/team-mappings.json maps a settings filename to enterprise team slugs; the file lives under copilot/teams/. A team omitting a value receives the enterprise default. GitHub says membership in multiple matching teams combines their values in the least restrictive direction before applying enterprise constraints.

Treat membership in an exception team as an access change. Keep non-negotiable rules outside team override, review overlapping memberships, and give each exception an owner and review date in your change record. Do not assume every baseline permission array is appended to the team's replacement array.

Across delivery methods, granular permissions compose restrictively. The usual MDM-before-server ordering has an explicit exception for permission rules and sandbox settings. A deny from another managed source still binds; sources declaring allowlists contribute an intersection. Deployment precedence and the permission reference describe these separately.

For example, suppose a team's server policy allows reading two fixture directories, while device policy allows only one. The wider team allowance cannot make the other directory prompt-free. Diagnose both source sets before widening the team rule again. If device policy denies that read, the result is a block, not an approval request.

Diagnose delivery before changing the rules#

Server-managed changes normally arrive within about an hour; restarting or signing in again triggers a refresh. Native MDM is checked hourly. Updated managed files require a client restart. These are the timings in GitHub's activation guidance, not a measured fleet rollout time.

SymptomFirst checks
One developer has no server policyLicense source, Usage billed to, supported session, selected governance organization, default branch, refresh result.
A local managed file has no effectExact path, valid JSON, file ownership and permissions, symlink rejection, restart.
A supposedly allowed operation asksOther declared allowlists, managed ask rules, and whether the request matches the intended selector.
A team exception still blocksA deny in another managed source, an ineligible override, or a team mapping that did not apply.
A policy changed but an old session behaves differentlyLoaded revision and refresh time for that session; compare with a newly refreshed one.

In VS Code, use Developer: Policy Diagnostics to inspect applied policy and Developer: Sync Account Policy when checking account-policy refresh. The enterprise guide describes these commands. A diagnostic showing configuration receipt should accompany, not replace, an observed operation decision.

Keep the reviewed policy commit, intended population, effective team membership, device policy payload, client/runtime version, refresh time, and fixture outcomes together. Exclude credentials and real source content. A reviewer should be able to explain a surprising decision from that record before anyone edits the policy.

Keep the execution boundary in the rollout decision#

An approval policy controls supported agent operations. Sandboxing restricts what the resulting process can access. The local sandbox documentation treats filesystem and network access as their own configuration. Review those restrictions before allowing a general-purpose interpreter or package script to run unattended. For connected tools, use the separate MCP server security review.

Approve each deployment group only after it has a supported session type, a confirmed policy source, and explainable acceptance results. If an essential restriction depends on a server response that might be absent, move that restriction into an appropriate device or downstream control before expanding the group.

Frequently asked questions

  • Why are Copilot managed settings not applying to a user?

    Check the supported client and session type, designated governance source, default branch, policy refresh, and Copilot license source. Server-managed settings follow the account's enterprise license. Users with multiple billing sources should check Usage billed to. Device delivery has different loading and file requirements.

  • Can a team exception override an MDM deny rule?

    No. Team specialization changes eligible server-managed values. A deny from another applicable managed source still blocks the operation. Team membership resolution and composition across delivery methods are separate steps.

  • Does disabling bypass mode prove granular permissions work?

    No. GitHub documents broader VS Code support for disableBypassPermissionsMode than for granular rules, which it limits to Agent Host sessions. Verify an actual deny and a repeated ask on the intended client and session type.

Browse all