mirror of
https://github.com/ZHANGTIANYAO1/teamspeak-music-bot.git
synced 2026-10-02 04:52:50 +08:00
fix(web): break infinite recursion in apiFetch by capturing nativeFetch
apiFetch called window.fetch which installApiClient had reassigned to call apiFetch — every request blew the stack. Capture the native fetch at module load (before any wrap) and use it inside apiFetch. Symptom: first-run / login redirect never fires because the router guard hangs on session.refresh(). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
1 parent
a8b056d2aa
commit
f46b37192f
1 file changed
+5
-4
+5
-4
@@ -2,11 +2,14 @@ import router from '../router/index.js';
|
||||
import { useSession } from '../composables/useSession.js';
|
||||
|
||||
let installed = false;
|
||||
const nativeFetch: typeof window.fetch = window.fetch.bind(window);
|
||||
|
||||
/**
|
||||
* Wraps fetch so every call:
|
||||
* - sends cookies (`credentials: 'same-origin'`)
|
||||
* - on 401 from /api/*: clear local session, redirect to /login
|
||||
*
|
||||
* Always uses the captured native fetch, never the (possibly wrapped) global.
|
||||
*/
|
||||
export function apiFetch(input: RequestInfo | URL, init: RequestInit = {}): Promise<Response> {
|
||||
const merged: RequestInit = {
|
||||
@@ -14,7 +17,7 @@ export function apiFetch(input: RequestInfo | URL, init: RequestInit = {}): Prom
|
||||
...init,
|
||||
headers: { ...(init.headers ?? {}) },
|
||||
};
|
||||
return fetch(input, merged).then(async (res) => {
|
||||
return nativeFetch(input, merged).then(async (res) => {
|
||||
if (res.status === 401 && shouldTriggerRefresh(input)) {
|
||||
const session = useSession();
|
||||
await session.refresh();
|
||||
@@ -39,10 +42,8 @@ function shouldTriggerRefresh(input: RequestInfo | URL): boolean {
|
||||
export function installApiClient(): void {
|
||||
if (installed) return;
|
||||
installed = true;
|
||||
const original = window.fetch.bind(window);
|
||||
window.fetch = ((input: RequestInfo | URL, init?: RequestInit) => {
|
||||
return apiFetch(input, init ?? {});
|
||||
}) as typeof window.fetch;
|
||||
// Keep original accessible if anything needs to bypass
|
||||
(window as unknown as { __originalFetch?: typeof fetch }).__originalFetch = original;
|
||||
(window as unknown as { __originalFetch?: typeof fetch }).__originalFetch = nativeFetch;
|
||||
}
|
||||
Reference in new issue
Block a user