fix: preserve dev frontend auth cookies

This commit is contained in:
Codex
2026-05-18 13:00:55 +00:00
parent 82f51f8601
commit c09beb0d54
3 changed files with 74 additions and 1 deletions
+72
View File
@@ -114,6 +114,7 @@ const DATABASE_CHECK_NAMES = [
const FRONTEND_CHECK_NAMES = [
"frontend:login-provider-visible",
"frontend:public-provider-info-visible",
"frontend:dev-auth-api-cookie",
"frontend:sidebar-collapse",
"frontend:mobile-nav-fixed-height",
"frontend:mobile-content-top-aligned",
@@ -1423,6 +1424,7 @@ async function frontendCheck(config: UniDeskConfig, urls: PublicUrls, checks: E2
"frontend:overview-pgdata-visible",
"frontend:no-naked-json-before-click",
]) || needPendingTask || needTaskHistory;
const needDevAuthApiCookie = wants("frontend:dev-auth-api-cookie");
const needRawProviderJson = wantsAny([
"frontend:public-provider-info-visible",
"frontend:raw-json-explicit-button",
@@ -1502,6 +1504,7 @@ async function frontendCheck(config: UniDeskConfig, urls: PublicUrls, checks: E2
let mobileRailMin = 0;
let mobileContentMetrics = { pageTop: 0, emptyTextOffset: 0 };
let bodyText = "";
let devAuthApiMetrics: any = { checked: false };
let rawBlocksBefore = 0;
let nakedJsonText = false;
let pendingTaskText = "";
@@ -2895,7 +2898,76 @@ async function frontendCheck(config: UniDeskConfig, urls: PublicUrls, checks: E2
&& Number(headerIndexByNodeId.get(edge.source)) >= Number(headerIndexByNodeId.get(edge.target)))
: [];
const metNonlinearTextLower = metNonlinearInitialText.toLowerCase();
if (needDevAuthApiCookie) {
const devFrontendUrl = `http://${config.network.publicHost}:${config.network.devFrontend.port}`;
const cookieJar = await page.context().cookies([devFrontendUrl]);
const authContext = await browser.newContext({ viewport: { width: 1440, height: 920 } });
await authContext.addCookies(cookieJar);
const devPage = await authContext.newPage();
devPage.on("console", (message) => {
if (message.type() === "error") consoleErrors.push(message.text());
});
devPage.on("pageerror", (error) => consoleErrors.push(error.message));
devPage.on("dialog", (dialog) => dialog.accept());
await devPage.goto(devFrontendUrl, { waitUntil: "domcontentloaded", timeout: 15000 });
await devPage.waitForSelector('[data-testid="app-shell"]', { timeout: 10000 }).catch(() => undefined);
await devPage.waitForTimeout(1200);
const authenticatedDevResponse = await devPage.evaluate(async () => {
const response = await fetch("/api/microservices", { credentials: "same-origin" });
const body = await response.json().catch(() => null);
return {
status: response.status,
ok: response.ok,
body,
};
});
const devUiState = await devPage.evaluate(() => {
const appShell = document.querySelector('[data-testid="app-shell"]');
const connText = document.querySelector('[data-testid="conn-text"]')?.textContent || "";
return {
appShellVisible: Boolean(appShell),
connText,
};
});
await authContext.close();
const unauthContext = await browser.newContext({ viewport: { width: 1440, height: 920 } });
const unauthPage = await unauthContext.newPage();
await unauthPage.goto(devFrontendUrl, { waitUntil: "domcontentloaded", timeout: 15000 });
const unauthenticatedDevResponse = await unauthPage.evaluate(async () => {
const response = await fetch("/api/microservices", { credentials: "same-origin" });
const body = await response.json().catch(() => null);
return {
status: response.status,
ok: response.ok,
body,
};
});
await unauthContext.close();
devAuthApiMetrics = {
checked: true,
devOrigin: devFrontendUrl,
productionSmoke: {
frontendUrl: urls.frontendUrl,
landedUrl,
publicFrontendReached,
},
authenticated: authenticatedDevResponse,
ui: devUiState,
unauthenticated: unauthenticatedDevResponse,
};
}
addSelectedCheck(checks, options, "frontend:login-provider-visible", bodyText.includes(config.providerGateway.id) && bodyText.includes(config.providerGateway.name) && bodyText.includes("核心在线"), { screenshotPath });
addSelectedCheck(checks, options, "frontend:dev-auth-api-cookie",
devAuthApiMetrics.checked === true
&& devAuthApiMetrics.authenticated?.ok === true
&& devAuthApiMetrics.authenticated?.status !== 401
&& Array.isArray(devAuthApiMetrics.authenticated?.body?.microservices)
&& devAuthApiMetrics.ui?.appShellVisible === true
&& String(devAuthApiMetrics.ui?.connText || "").includes("核心在线")
&& devAuthApiMetrics.productionSmoke?.publicFrontendReached === true
&& devAuthApiMetrics.unauthenticated?.status === 401
&& String(devAuthApiMetrics.unauthenticated?.body?.error || "") === "authentication required",
{ devAuthApiMetrics });
addSelectedCheck(checks, options, "frontend:public-provider-info-visible", publicFrontendReached && bodyText.includes(config.providerGateway.id) && bodyText.includes(config.providerGateway.name) && rawText.includes('"status": "online"') && rawText.includes(`"providerId": "${config.providerGateway.id}"`), { frontendUrl: urls.frontendUrl, landedUrl, providerId: config.providerGateway.id, rawTextPreview: rawText.slice(0, 400) });
addSelectedCheck(checks, options, "frontend:sidebar-collapse", railWidthBefore >= 160 && railWidthCollapsed <= 70, { railWidthBefore, railWidthCollapsed });
addSelectedCheck(checks, options, "frontend:mobile-nav-fixed-height", mobileRailHeights.length > 0 && mobileRailMax - mobileRailMin <= 1 && mobileRailMax <= 44, { mobileRailHeights });
@@ -22,6 +22,7 @@ const PROVIDER_HTTP_TUNNEL_MAX_ATTEMPTS: i32 = 3;
const FORWARD_REQUEST_HEADERS: &[&str] = &[
"accept",
"content-type",
"cookie",
"range",
"x-auth",
"x-requested-with",
@@ -1229,7 +1229,7 @@ async function serviceDiagnostics(service: ManagedService): Promise<JsonRecord>
function forwardHeaders(request: Request): Headers {
const headers = new Headers();
for (const name of ["accept", "content-type", "x-requested-with"]) {
for (const name of ["accept", "content-type", "cookie", "x-requested-with"]) {
const value = request.headers.get(name);
if (value !== null) headers.set(name, value);
}