Repository navigation
Description
Summary
With the GitHub Copilot provider, the first prompt sent after a Location has been evicted for inactivity fails with Provider request failed with HTTP 404. The Location reboots about 0.3 to 0.5 s before the failure, and provider.updated / model.updated fire right after it. Sending the same prompt again succeeds. This happens several times a day for anyone who steps away for more than about an hour.
Environment
- opencode version: 2.0.26 (also seen on 2.0.18)
- OS: Darwin 25.6.0 (macOS, arm64)
- Terminal: Apple Terminal (TERM=xterm-256color, COLORTERM=truecolor)
- Shell: /bin/bash
- Install/channel: latest, managed background service
- Active plugins: none configured
- Provider/model:
github-copilot/claude-opus-5.5(variantmedium), OAuth login
Reproduction
- Use the
github-copilotprovider with any model (seen withclaude-opus-5.5). - Leave the session idle until its Location is evicted (
location services evictedin the log, about 60 minutes). - Send a prompt in that session, or start a new session in the same directory.
- The prompt fails with
Provider request failed with HTTP 404. - Send the prompt again. It succeeds.
Expected Behavior
The first prompt after a Location reboots should wait for the provider to be ready, or retry once, instead of failing.
Actual Behavior
The prompt fails immediately with:
Failed to drain Session cause="AI.Error: Provider request failed with HTTP 404
[cause]: AI.Error.InvalidRequest: Provider request failed with HTTP 404
[cause]: AI_APICallError:
The AI_APICallError has an empty message, and the log doesn't include the request URL or the response body.
Additional Context
Every 404 in the log follows the same pattern: Location evicted, then idle, then the Location boots on the next prompt, then the 404 comes about 0.5 s later, then provider.updated and model.updated. Timestamps are UTC.
| 404 at | Location booted | Last evicted | Version |
|---|---|---|---|
| 2026-10-12 15:48:39.046 | 15:48:38.619 | 15:29:46 | 2.0.18 |
| 2026-10-12 18:44:10.921 | 18:44:10.493 | 18:35:46 | 2.0.18 |
| 2026-10-12 19:59:13.780 | 19:59:13.292 | 19:48:46 | 2.0.18 |
| 2026-10-12 21:35:26.609 | 21:35:26.147 | 21:06:47 | 2.0.18 |
| 2026-10-13 13:38:35.875 | 13:38:35.536 | 10-12 22:57:47 | 2.0.18 |
| 2026-10-13 16:25:55.295 | 16:25:54.960 | 15:04:50 | 2.0.18 |
| 2026-10-13 19:09:29.073 | 19:09:28.603 | 18:20:50 | 2.0.18 |
| 2026-10-13 20:18:08.066 | 20:18:07.730 | 20:12:51 | 2.0.18 |
| 2026-10-14 13:48:30.909 | 13:48:30.582 | 10-13 22:49:51 | 2.0.18 |
| 2026-10-14 13:49:47.710 | 13:49:47.204 | (service restarted on upgrade) | 2.0.26 |
| 2026-10-14 16:22:44.239 | 16:22:43.815 | 16:04:47 | 2.0.26 |
| 2026-10-14 17:53:35.032 | 17:53:34.684 | 17:33:47 | 2.0.26 |
Log excerpt from the most recent occurrence on 2.0.26 (paths redacted):
17:53:34.323Z location services booted directory=<project> durationMs=86
17:53:34.503Z event provider.updated
17:53:34.507Z event model.updated
17:53:34.684Z location services booted directory=<home> durationMs=38
17:53:34.726Z event provider.updated
17:53:34.728Z event model.updated
17:53:35.032Z ERROR Failed to drain Session cause="AI.Error: Provider request failed with HTTP 404 ..."
17:53:35.253Z event provider.updated
17:53:35.259Z event model.updated
17:53:35.423Z event provider.updated
17:53:35.429Z event model.updated
This looks related to #51701, where /api/model and /api/provider return an incomplete catalog right after a Location reboots following idle eviction. Here the symptom is a failed Copilot model request instead: the Copilot provider seems to send the first request before its token or endpoint has been refreshed.
The 404 also happened on the first prompt of a brand-new session, so stale conversation state isn't the cause. The only workaround is to resend the prompt.
Activity
opencode-agent commentedon Oct 14, 2026
Thanks for the detailed report and timeline, they made this easy to track down.
I reproduced it on 2.0.26 with a mocked Copilot endpoint, starting OpenCode cold each time the way a Location reboots after eviction. If a prompt arrives before the Copilot plugin has finished loading its model list, Claude models fall back to the models.dev settings. On 2.0.26 that fallback sends the request through the Copilot SDK to
https://api.githubcopilot.com/v1/chat/completions. That path doesn't exist, so it returns a bare 404 (which is whyAI_APICallErroris empty). Once the model list has loaded, the correct route is used, which is why resending works.On the latest
dev(8ffbcc2c8), and also on the 2.0.29 release, the same early request goes to the Anthropic Messages endpoint (/v1/messages) instead, and the 404 no longer happens. The change is #54210, first released in 2.0.27. Upgrading to 2.0.27 or newer should fix this; please let us know if it doesn't.One caveat: a request sent during that short window still uses the default
api.githubcopilot.comhost, not your account's own Copilot endpoint. If your account uses a non-default endpoint (for example GitHub Enterprise or data residency), you might still see a failure there; if so, please say so here.Related: #51701 (empty model/provider catalog while a Location reboots after idle eviction).
The bot will close this issue in 1 day unless you reply that it still happens on a newer version.
opencode-agent commentedon Oct 15, 2026
Closing this as fixed. I reproduced the
HTTP 404on the first Copilot prompt after a cold start on 2.0.26, but it doesn't happen on the latestdev(8ffbcc2c8) or on the 2.0.29 release. The fix is #54210 (first released in 2.0.27): Claude models no longer get sent to the missing/v1/chat/completionspath while the Copilot model list is still loading. We waited a day in case it still happened for you, and didn't hear back.If you still see this on 2.0.27 or newer, please comment here or open a new issue with your version and a log excerpt. That includes a first-request failure if your account uses a non-default Copilot endpoint, such as GitHub Enterprise. Thanks again for the detailed report and timeline!
StanPonomarev commentedon Nov 4, 2026
Still reproducible on v2.2.5 with GitHub Copilot Enterprise. This appears to be the non-default endpoint caveat mentioned above: the first request after a Location boots can use
api.githubcopilot.cominstead of the account’s Enterprise endpoint.Environment
--standalonemode; logs also show similar failures at shared-service startupgithub-copilot/gpt-6.1-solandgithub-copilot/claude-opus-5.5Reproduction
The failure occurs when a session continues immediately after moving to a new directory/Location. Instead of the original 404, it returns:
Some occurrences include:
Example timeline, UTC:
Endpoint race reproduced without a model request
Querying
/api/modelthree times sequentially for a fresh temporary directory showed:https://api.githubcopilot.comhttps://api.githubcopilot.com/v1https://copilot-api.<enterprise>.ghe.comhttps://copilot-api.<enterprise>.ghe.com/v1The stored credential already contains the correct Enterprise
apiEndpointmetadata. No credentials were changed during this test.Relevant v2.2.5 code
In
github-copilot.ts:loadedstarts empty.refresh()is forked in the background.load()derives the Enterprise URL from credential metadata before fetching/models, but assignsloaded.baseURLonly after that fetch completes or fails.This appears to leave a window where an immediately continuing session sends its Enterprise credential to the public endpoint. The actual destination of the historical failed requests wasn’t captured, but the catalog race above is directly reproduced and matches their timing.
Could this issue be reopened for the Enterprise-host case, or should it be tracked separately? Ideally, credential-derived routing would be initialized before models become usable, independently of asynchronous model discovery. Related: #38204 proposed awaiting initial Copilot sync but was closed without merging.