Basic Auth breaks the CORS support #7213

Open
opened 2026-02-16 18:06:28 -05:00 by yindo · 1 comment
Owner

Originally created by @Olli-palkkaus on GitHub (Jan 22, 2026).

Originally assigned to: @thdxr on GitHub.

Description

I am trying to create a simple web UI that connects from browser to Opencode API using @opencode-ai/sdk/client. This works anonymous, or same-server, but in a scenario where my Opencode server is in the network (and therefore I need to add basic auth) the code no longer works.

The issue is that when doing fetch with authentication headers (GET/POST etc.), browser will first make a preflight check (OPTIONS) and this is done without credentials. This now fails because basic authentication guards OPTIONS verb (all requests).

FIX: I believe , you could just fix this in server.ts by switching .use(cors(... (line 103) before the .use(..basicAuth( (line 80). I am not familiar with Hono, so perhaps someone should check this, but I am pretty sure that generally with CORS preflight (OPTIONS) should respond to anonymous calls and the order of these uses now breaks things.

Plugins

None

OpenCode version

"@opencode-ai/sdk": "^1.1.27", server is the docker from 2026-01-20

Steps to reproduce

To reproduce:

  • Client (browser) and server must be in different origins (domains) and server must be non-localhost
  • Add client cors to server or use localhost as client
  • Create a browser UI like below
  • Observe preflight failing. In more detail,

Code (taken form larger project. I can add a real example if necessary):


function fetchWithBasicAuth(input: RequestInfo | URL, init?: RequestInit) {
  const username = "opencode";
  const password = "pwdherefromsomeuserintput";
  return globalThis.fetch(input, {
    ...init,
    headers: {
      ...init?.headers,
      Authorization: `Basic ${btoa(`${username}:${password}`)}`,
    },
    credentials: "include",
  });
}

const client = createOpencodeClient({
    baseUrl: "https://myinstance-of-opencode.foobar.com",
    fetch: fetchWithBasicAuth,
  });

useEffect(() => {
    client.project.list().then((response) => {
      // THIS NOW FAILS
      setProjects(response.data ?? []);
    });

Screenshot and/or share link

No response

Operating System

Windows 11, Server is the current Docker.

Terminal

None

Originally created by @Olli-palkkaus on GitHub (Jan 22, 2026). Originally assigned to: @thdxr on GitHub. ### Description I am trying to create a simple web UI that connects from browser to Opencode API using @opencode-ai/sdk/client. This works anonymous, or same-server, but in a scenario where my Opencode server is in the network (and therefore I need to add basic auth) the code no longer works. The issue is that when doing fetch with authentication headers (GET/POST etc.), browser will first make a preflight check (OPTIONS) and this is done without credentials. This now fails because basic authentication guards OPTIONS verb (all requests). FIX: I believe , you could just fix this in `server.ts` by switching `.use(cors(...` (line 103) before the `.use(..basicAuth(` (line 80). I am not familiar with Hono, so perhaps someone should check this, but I am pretty sure that generally with CORS preflight (OPTIONS) should respond to anonymous calls and the order of these uses now breaks things. ### Plugins None ### OpenCode version "@opencode-ai/sdk": "^1.1.27", server is the docker from 2026-01-20 ### Steps to reproduce To reproduce: - Client (browser) and server must be in different origins (domains) and server must be non-localhost - Add client cors to server or use localhost as client - Create a browser UI like below - Observe preflight failing. In more detail, Code (taken form larger project. I can add a real example if necessary): ```js function fetchWithBasicAuth(input: RequestInfo | URL, init?: RequestInit) { const username = "opencode"; const password = "pwdherefromsomeuserintput"; return globalThis.fetch(input, { ...init, headers: { ...init?.headers, Authorization: `Basic ${btoa(`${username}:${password}`)}`, }, credentials: "include", }); } const client = createOpencodeClient({ baseUrl: "https://myinstance-of-opencode.foobar.com", fetch: fetchWithBasicAuth, }); useEffect(() => { client.project.list().then((response) => { // THIS NOW FAILS setProjects(response.data ?? []); }); ``` ### Screenshot and/or share link _No response_ ### Operating System Windows 11, Server is the current Docker. ### Terminal None
yindo added the bugweb labels 2026-02-16 18:06:28 -05:00
Author
Owner

@github-actions[bot] commented on GitHub (Jan 22, 2026):

This issue might be a duplicate of existing issues. Please check:

  • #9206: Web UI: Basic Auth incompatible with crossorigin attributes on assets
  • #8676: Plugin client returns 401 Unauthorized when OPENCODE_SERVER_PASSWORD is set (Desktop)
  • #9706: Plugin client missing Authorization header when OPENCODE_SERVER_PASSWORD is set

All of these issues relate to CORS and Basic Auth interaction in different contexts. #9206 specifically discusses CORS preflight (OPTIONS) requests being blocked by authentication, which aligns with your findings about the middleware order in server.ts.

Feel free to ignore if none of these address your specific case.

@github-actions[bot] commented on GitHub (Jan 22, 2026): This issue might be a duplicate of existing issues. Please check: - #9206: Web UI: Basic Auth incompatible with crossorigin attributes on assets - #8676: Plugin client returns 401 Unauthorized when OPENCODE_SERVER_PASSWORD is set (Desktop) - #9706: Plugin client missing Authorization header when OPENCODE_SERVER_PASSWORD is set All of these issues relate to CORS and Basic Auth interaction in different contexts. #9206 specifically discusses CORS preflight (OPTIONS) requests being blocked by authentication, which aligns with your findings about the middleware order in server.ts. Feel free to ignore if none of these address your specific case.
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: anomalyco/opencode#7213