fix: fix auth provider caching

This commit is contained in:
Abhishek Kumar 2026-06-18 17:34:48 +05:30
parent 2939726b2c
commit d60065bf0a
3 changed files with 22 additions and 7 deletions

View file

@ -211,9 +211,13 @@ services:
ui:
image: ${REGISTRY:-dograhai}/dograh-ui:latest
environment:
# Bind the Next.js standalone server to all interfaces
HOSTNAME: "0.0.0.0"
# Server-side URL (SSR, internal Docker network)
BACKEND_URL: "${BACKEND_URL:-http://api:8000}"
NODE_ENV: "oss"
# Flag to enable/ disable posthog
ENABLE_TELEMETRY: "${ENABLE_TELEMETRY:-true}"
@ -229,7 +233,7 @@ services:
test:
[
"CMD-SHELL",
"wget --no-verbose --tries=1 --spider http://localhost:3010 || exit 1",
"wget --no-verbose --tries=1 --spider http://127.0.0.1:3010 || exit 1",
]
interval: 30s
timeout: 10s

View file

@ -49,11 +49,14 @@ async function resolveAuthConfig(): Promise<ResolvedAuthConfig> {
return cachedConfig;
}
} catch {
// Backend not reachable — fall back to local
// Backend not reachable — fall through without caching so we retry next request.
}
cachedConfig = { authProvider: "local", stackConfig: null };
return cachedConfig;
// Unknown (backend unreachable). Return the local fallback for THIS request but
// do NOT cache it: caching here would pin the entire UI to local auth until a
// container restart if the first resolution loses the startup race with the api
// service. Leaving it uncached means the next request retries and self-heals.
return { authProvider: "local", stackConfig: null };
}
/**

View file

@ -20,15 +20,23 @@ async function fetchAuthProvider(): Promise<string> {
const res = await fetch(`${backendUrl}/api/v1/health`);
if (res.ok) {
const data = await res.json();
// Only cache a DEFINITIVE answer from the backend. Never cache a failure:
// this is a module-scoped cache with no TTL, so a single early request
// during container startup (before the api service is reachable) would
// otherwise poison it to 'local' for the life of the worker — redirecting
// every Stack user to the local /auth/login form even though the backend
// reports `stack`.
cachedAuthProvider = (data.auth_provider as string) || 'local';
return cachedAuthProvider;
}
} catch {
// Backend not reachable — fall back to local
// Backend not reachable — fall through without caching so we retry next request.
}
cachedAuthProvider = 'local';
return cachedAuthProvider;
// Provider unknown (backend unreachable). Return a non-'local' sentinel so the
// middleware does NOT guard/redirect: assuming 'local' here would bounce Stack
// users to /auth/login. Deliberately not cached — the next request retries.
return 'unknown';
}
export async function middleware(request: NextRequest) {