Skip to content

Remote MCP OAuth (Microsoft Entra): calls fail after the access token expires while mcp.list still says connected; only restartServer recovers #5366

Open

Description

@vikramgorla

I use remote MCP servers protected by Microsoft Entra ID (Teams, Outlook mail) through the Copilot SDK (@github/copilot-sdk 1.0.24, runtime 1.0.101), with mcpOAuthTokenStorage: "persistent" and the runtime's own sign-in (mcp.oauth.login); the host never handles OAuth tokens.

What happens: roughly 60–90 minutes after sign-in (the Entra access-token lifetime), tool calls to these servers start failing as unauthorized. session.rpc.mcp.list() keeps reporting them as connected. The agent then decides it cannot use the server and carries on without it. rpc.mcp.restartServer({ name }) fixes it at once with no browser sign-in, so the stored refresh token is still valid.

Reproduced locally (no account involved): a local OAuth-protected MCP test server that issues 20-second access tokens, returns HTTP 401 on an expired token and supports refresh tokens. After the access token expires:

  • every call fails with "MCP OAuth challenge required (HTTP 401)";
  • mcp.list() stays connected for the whole time watched (60 s+);
  • on runtime 1.0.101 the runtime makes no refresh request of its own and never recovers; on runtime 1.0.103 it sends a needs-auth status event and retries refresh grants, but calls still keep failing;
  • restartServer makes the next call succeed.

Expected: like the VS Code MCP client, refresh the access token with the stored refresh token on a 401 (or shortly before expiry), retry the call once, and keep the server usable. At minimum, report the server as needs-auth/failed in mcp.list() instead of connected once its token is rejected.

Note: registering onMcpAuthRequest and answering { kind: "runtimeRefresh" } for reason refresh did not fix calls either in my test, and it changes the behaviour for initial requests (a stored sign-in no longer reconnects at start when initial is cancelled), so it is not a host-side workaround.

Environment: macOS 26 and Linux; SDK 1.0.24 / runtime 1.0.101, also checked on SDK 1.0.26 / runtime 1.0.103.

Activity

  1. added
    area:mcpMCP server configuration, discovery, connectivity, OAuth, policy, and registry
    area:non-interactiveNon-interactive mode (-p), CI/CD, ACP protocol, and headless automation
    and removed on Nov 6, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    area:mcpMCP server configuration, discovery, connectivity, OAuth, policy, and registryarea:non-interactiveNon-interactive mode (-p), CI/CD, ACP protocol, and headless automation

    Type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions