Skip to content

Commit 1aaa559

Browse files
committed
Fixed OAuth error when 401 comes from initialize (instead of connect, as is more common). Also, now we automatically start auth when auth required (instead of just bringing up the auth ux and making the user push a button). This should be at parity with how v1 works.
1 parent 57af0c9 commit 1aaa559

3 files changed

Lines changed: 37 additions & 13 deletions

File tree

core/mcp/remote/node/server.ts

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -461,11 +461,11 @@ export function createRemoteApp(
461461
} catch (err) {
462462
// transport.start() threw - this is the expected failure path
463463
const msg = err instanceof Error ? err.message : String(err);
464-
// Preserve 401 status if the underlying error is a 401
465-
const is401 =
466-
(err as { code?: number }).code === 401 ||
467-
msg.includes("401") ||
468-
msg.includes("Unauthorized");
464+
// Preserve 401 only when the transport/SDK reports it (no message guessing)
465+
const status =
466+
(err as { code?: number; status?: number }).code ??
467+
(err as { code?: number; status?: number }).status;
468+
const is401 = status === 401;
469469
return c.json(
470470
{ error: `Failed to start transport: ${msg}` },
471471
is401 ? 401 : 500,
@@ -509,7 +509,12 @@ export function createRemoteApp(
509509
return c.json({ ok: true });
510510
} catch (err) {
511511
const msg = err instanceof Error ? err.message : String(err);
512-
return c.json({ error: msg }, 500);
512+
// Preserve 401 only when the transport/SDK reports it (no message guessing)
513+
const status =
514+
(err as { code?: number; status?: number }).code ??
515+
(err as { code?: number; status?: number }).status;
516+
const is401 = status === 401;
517+
return c.json({ error: msg }, is401 ? 401 : 500);
513518
}
514519
});
515520

core/mcp/remote/remoteClientTransport.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -294,7 +294,9 @@ export class RemoteClientTransport implements Transport {
294294

295295
if (!res.ok) {
296296
const text = await res.text();
297-
throw new Error(`Remote send failed (${res.status}): ${text}`);
297+
const error = new Error(`Remote send failed (${res.status}): ${text}`);
298+
(error as { status?: number }).status = res.status;
299+
throw error;
298300
}
299301
}
300302

web/src/App.tsx

Lines changed: 23 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -547,12 +547,29 @@ const App = () => {
547547
try {
548548
await client.connect();
549549
} catch (error) {
550-
const message = error instanceof Error ? error.message : String(error);
551-
toast({
552-
title: "Connection failed",
553-
description: message,
554-
variant: "destructive",
555-
});
550+
const status = (error as { status?: number }).status;
551+
if (status === 401) {
552+
try {
553+
await client.authenticate();
554+
} catch (authError) {
555+
setIsAuthDebuggerVisible(true);
556+
toast({
557+
title: "Authentication required",
558+
description:
559+
authError instanceof Error
560+
? authError.message
561+
: String(authError),
562+
variant: "destructive",
563+
});
564+
}
565+
} else {
566+
const message = error instanceof Error ? error.message : String(error);
567+
toast({
568+
title: "Connection failed",
569+
description: message,
570+
variant: "destructive",
571+
});
572+
}
556573
if (client.getStatus() === "connecting") {
557574
await client.disconnect();
558575
}

0 commit comments

Comments
 (0)