copilot_chat: Exchange OAuth token for session token before API calls#57738
Open
eodus wants to merge 1 commit into
Open
copilot_chat: Exchange OAuth token for session token before API calls#57738eodus wants to merge 1 commit into
eodus wants to merge 1 commit into
Conversation
|
We require contributors to sign our Contributor License Agreement, and we don't have @eodus on file. You can sign our CLA at https://zed.dev/cla. Once you've signed, post a comment here that says '@cla-bot check'. |
Contributor
Author
|
@cla-bot check |
|
The cla-bot has been summoned, and re-checked this pull request! |
Zed currently uses the raw OAuth token (ghu_...) directly in Copilot API requests. All other Copilot clients (VS Code, Claude Code, OpenCode) exchange this token for a short-lived session token via GET /copilot_internal/v2/token before making API calls. The session token carries integrator identity and is required for the full model catalog on enterprise endpoints. Without it, the server defaults to a degraded model list based on the OAuth app registration. This change: - Adds exchange_session_token() that calls the token exchange endpoint - Caches the session token with TTL-based refresh (5 min before expiry) - Uses the session token for model catalog fetches and all API calls - Falls back gracefully to raw OAuth token if exchange fails - Adds Copilot-Integration-Id header required by enterprise endpoints Fixes zed-industries#57219
55ec166 to
60a5eac
Compare
eodus
added a commit
to eodus/zed
that referenced
this pull request
May 26, 2026
The Copilot SDK migrated token storage from apps.json to a SQLite auth.db. Zed's copilot_chat only reads apps.json/hosts.json, so users who sign in with the newer SDK get no OAuth token and no models. This change: - Adds sqlez dependency to copilot_chat for SQLite reading - Adds extract_oauth_token_from_db() that reads auth.db via sqlez - Tries auth.db at startup (constructor) if env var is not set - Tries auth.db as fallback in the file watcher callback when apps.json/hosts.json don't contain a token - Validates token starts with ghu_ before accepting Related to zed-industries#57219 (complements the session token exchange in zed-industries#57738) Release Notes: - Fixed GitHub Copilot authentication for users whose SDK stores tokens in auth.db instead of apps.json
eodus
added a commit
to eodus/zed
that referenced
this pull request
May 26, 2026
The Copilot SDK migrated token storage from apps.json to a SQLite auth.db. Zed's copilot_chat only reads apps.json/hosts.json, so users who sign in with the newer SDK get no OAuth token and no models. This change: - Adds sqlez dependency to copilot_chat for SQLite reading - Adds extract_oauth_token_from_db() that reads auth.db via sqlez - Tries auth.db at startup (constructor) if env var is not set - Tries auth.db as fallback in the file watcher callback when apps.json/hosts.json don't contain a token - Validates token starts with ghu_ before accepting Related to zed-industries#57219 (complements the session token exchange in zed-industries#57738) Release Notes: - Fixed GitHub Copilot authentication for users whose SDK stores tokens in auth.db instead of apps.json
eodus
added a commit
to eodus/zed
that referenced
this pull request
May 26, 2026
The Copilot SDK migrated token storage from apps.json to a SQLite auth.db. Zed's copilot_chat only reads apps.json/hosts.json, so users who sign in with the newer SDK get no OAuth token and no models. This change: - Adds sqlez dependency to copilot_chat for SQLite reading - Adds extract_oauth_token_from_db() that reads auth.db via sqlez - Tries auth.db at startup (constructor) if env var is not set - Tries auth.db as fallback in the file watcher callback when apps.json/hosts.json don't contain a token - Validates token starts with ghu_ before accepting Related to zed-industries#57219 (complements the session token exchange in zed-industries#57738) Release Notes: - Fixed GitHub Copilot authentication for users whose SDK stores tokens in auth.db instead of apps.json
eodus
added a commit
to eodus/zed
that referenced
this pull request
May 26, 2026
The Copilot SDK migrated token storage from apps.json to a SQLite auth.db. Zed's copilot_chat only reads apps.json/hosts.json, so users who sign in with the newer SDK get no OAuth token and no models. This change: - Adds sqlez dependency to copilot_chat for SQLite reading - Adds extract_oauth_token_from_db() that reads auth.db via sqlez - Tries auth.db at startup (constructor) if env var is not set - Tries auth.db as fallback in the file watcher callback when apps.json/hosts.json don't contain a token - Validates token starts with ghu_ before accepting Related to zed-industries#57219 (complements the session token exchange in zed-industries#57738) Release Notes: - Fixed GitHub Copilot authentication for users whose SDK stores tokens in auth.db instead of apps.json
eodus
added a commit
to eodus/zed
that referenced
this pull request
May 26, 2026
The Copilot SDK migrated token storage from apps.json to a SQLite auth.db. Zed's copilot_chat only reads apps.json/hosts.json, so users who sign in with the newer SDK get no OAuth token and no models. This change: - Adds sqlez dependency to copilot_chat for SQLite reading - Adds extract_oauth_token_from_db() that reads auth.db via sqlez - Tries auth.db at startup (constructor) if env var is not set - Tries auth.db as fallback in the file watcher callback when apps.json/hosts.json don't contain a token - Validates token starts with ghu_ before accepting Related to zed-industries#57219 (complements the session token exchange in zed-industries#57738) Release Notes: - Fixed GitHub Copilot authentication for users whose SDK stores tokens in auth.db instead of apps.json
Contributor
|
This is fixed by #57764 |
Contributor
Author
|
@morgankrey no, that is a separate issue! If you use just API key (not a temporary key!) copilot server returns truncated list of the models. That probably affects corporate users only. The scheme I implemented repeats Vscode auth scheme and other tools. That results into the full model list |
Contributor
|
Sorry - got confused |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Implements Copilot session token exchange in
copilot_chat, matching the protocol used by all other Copilot clients (VS Code, JetBrains, Neovim plugins).Problem
Zed's
copilot_chatcrate currently uses the raw OAuth token (ghu_...) directly in Copilot API requests. The Copilot backend expects clients to first exchange this token for a short-lived session token viaGET /copilot_internal/v2/token. Without this exchange, the server falls back to a degraded model catalog based on the OAuth app registration, causing users to see no models or a reduced set.This is the root cause of #57219 for users who have successfully authenticated (i.e. have a valid OAuth token in
apps.json).Solution
exchange_session_token()that calls the/copilot_internal/v2/tokenendpointupdate_models()andget_auth_details()for all downstream API callsCopilot-Integration-Idheader required by enterprise endpoints when using session tokens#[serde(default)]onModelBillingfields that enterprise endpoints may omitNotes
Copilot-Integration-Id: vscode-chatvalue is the de facto standard used by all third-party Copilot integrations — no per-client integration ID exists for non-VS Code clients.oauth_tokenparameter name incopilot_request_headers()now sometimes carries a session token rather than an OAuth token. A naming cleanup could be done in a follow-up PR to keep this one focused on the functional fix.Related issue:
apps.json→auth.dbmigrationThere may be a separate contributing factor to #57219: the Copilot SDK appears to have migrated OAuth token storage from
apps.json(whichcopilot_chatcurrently reads) to a SQLiteauth.db. Users who authenticated before this migration have a workingapps.jsonand hit only the token exchange bug (fixed by this PR). Users on a fresh install may not getapps.jsoncreated at all, which is a separate auth-layer issue. This PR focuses on the token exchange; theauth.dbmigration would be a separate change.Fixes #57219
Release Notes: