From d43787a96dcf3de5d1f4e5c36076a217e4c8982c Mon Sep 17 00:00:00 2001 From: chan Date: Fri, 29 May 2026 16:53:26 +0900 Subject: [PATCH] test(adminfront): fix audit mock conflict and stabilize tenant dropdown interaction --- adminfront/tests/audit.spec.ts | 79 ++++++++++++++------------------ adminfront/tests/tenants.spec.ts | 10 ++-- 2 files changed, 40 insertions(+), 49 deletions(-) diff --git a/adminfront/tests/audit.spec.ts b/adminfront/tests/audit.spec.ts index c0e2573d..cdc4273c 100644 --- a/adminfront/tests/audit.spec.ts +++ b/adminfront/tests/audit.spec.ts @@ -57,6 +57,19 @@ test.describe("Audit Logs Management", () => { headers: { "Access-Control-Allow-Origin": "*" }, }); } + if (url.includes("/v1/audit")) { + const urlObj = new URL(url); + const cursor = urlObj.searchParams.get("cursor"); + const offset = cursor ? 20 : 0; + return route.fulfill({ + json: { + items: generateMockLogs(20, offset), + next_cursor: offset === 0 ? "fake-cursor" : null, + total: 40, + }, + headers: { "Access-Control-Allow-Origin": "*" }, + }); + } return route.continue(); }); }); @@ -82,13 +95,6 @@ test.describe("Audit Logs Management", () => { }; test("should load initial logs and display correctly", async ({ page }) => { - await page.route("**/v1/audit*", async (route) => { - return route.fulfill({ - json: { items: generateMockLogs(20, 0), total: 20 }, - headers: { "Access-Control-Allow-Origin": "*" }, - }); - }); - await page.goto("/audit-logs"); // Check header @@ -100,49 +106,35 @@ test.describe("Audit Logs Management", () => { await expect(page.locator("tbody tr")).toHaveCount(20, { timeout: 15000 }); // Check specific data visible in the row - await expect(page.locator("tbody")).toContainText("user-even"); - await expect(page.locator("tbody")).toContainText("CREATE_TENANT"); + await expect(page.locator("tbody")).toContainText("user-even", { + timeout: 10000, + }); + await expect(page.locator("tbody")).toContainText("CREATE_TENANT", { + timeout: 10000, + }); }); test("should load more logs on scroll (infinite scroll)", async ({ page, }) => { - let callCount = 0; - await page.route("**/v1/audit*", async (route) => { - const logs = generateMockLogs(20, callCount * 20); - callCount++; - return route.fulfill({ - json: { - items: logs, - next_cursor: callCount < 2 ? "fake-cursor" : null, - }, - headers: { "Access-Control-Allow-Origin": "*" }, - }); - }); - await page.goto("/audit-logs"); await expect(page.locator("tbody tr")).toHaveCount(20, { timeout: 15000 }); const loadMoreBtn = page.getByRole("button", { name: /더 보기|Load more/i, }); - await expect(loadMoreBtn).toBeVisible(); + await expect(loadMoreBtn).toBeVisible({ timeout: 10000 }); await loadMoreBtn.click(); // Wait for the next page to load await expect(page.locator("tbody tr")).toHaveCount(40, { timeout: 15000 }); // user-even and CREATE_TENANT should still be visible in the newly loaded rows - await expect(page.locator("tbody")).toContainText("user-even"); + await expect(page.locator("tbody")).toContainText("user-even", { + timeout: 10000, + }); }); test("should filter logs by Action and User ID locally", async ({ page }) => { - await page.route("**/v1/audit*", async (route) => { - return route.fulfill({ - json: { items: generateMockLogs(20, 0), total: 20 }, - headers: { "Access-Control-Allow-Origin": "*" }, - }); - }); - await page.goto("/audit-logs"); await expect(page.locator("tbody tr")).toHaveCount(20, { timeout: 15000 }); @@ -152,30 +144,27 @@ test.describe("Audit Logs Management", () => { await userIdInput.fill("user-even"); // Playwright expect will retry, so it will wait for deferred value - await expect(page.locator("tbody tr")).toHaveCount(10, { timeout: 10000 }); - await expect(page.locator("tbody")).not.toContainText("user-odd"); + await expect(page.locator("tbody tr")).toHaveCount(10, { timeout: 15000 }); + await expect(page.locator("tbody")).not.toContainText("user-odd", { + timeout: 10000, + }); // Clear User ID await userIdInput.clear(); - await expect(page.locator("tbody tr")).toHaveCount(20, { timeout: 10000 }); + await expect(page.locator("tbody tr")).toHaveCount(20, { timeout: 15000 }); // Search by Action const actionInput = page.getByTestId("audit-search-action"); await actionInput.fill("ROTATE_SECRET"); // Check that we only see ROTATE_SECRET (20 - 7 = 13) - await expect(page.locator("tbody tr")).toHaveCount(13, { timeout: 10000 }); - await expect(page.locator("tbody")).not.toContainText("CREATE_TENANT"); + await expect(page.locator("tbody tr")).toHaveCount(13, { timeout: 15000 }); + await expect(page.locator("tbody")).not.toContainText("CREATE_TENANT", { + timeout: 10000, + }); }); test("should filter logs by Status locally", async ({ page }) => { - await page.route("**/v1/audit*", async (route) => { - return route.fulfill({ - json: { items: generateMockLogs(20, 0), total: 20 }, - headers: { "Access-Control-Allow-Origin": "*" }, - }); - }); - await page.goto("/audit-logs"); await expect(page.locator("tbody tr")).toHaveCount(20, { timeout: 15000 }); @@ -184,12 +173,12 @@ test.describe("Audit Logs Management", () => { // ID % 5 === 0 are status "failure" // IDs: 0, 5, 10, 15 => 4 items - await expect(page.locator("tbody tr")).toHaveCount(4, { timeout: 10000 }); + await expect(page.locator("tbody tr")).toHaveCount(4, { timeout: 15000 }); // Select "Success" status await page.getByTestId("audit-filter-status").selectOption("success"); // IDs: 1,2,3,4, 6,7,8,9, 11,12,13,14, 16,17,18,19 => 16 items - await expect(page.locator("tbody tr")).toHaveCount(16, { timeout: 10000 }); + await expect(page.locator("tbody tr")).toHaveCount(16, { timeout: 15000 }); }); }); diff --git a/adminfront/tests/tenants.spec.ts b/adminfront/tests/tenants.spec.ts index eec5956f..19d76532 100644 --- a/adminfront/tests/tenants.spec.ts +++ b/adminfront/tests/tenants.spec.ts @@ -651,7 +651,7 @@ test.describe("Tenants Management", () => { const exportMenuItem = page.getByTestId("tenant-export-menu-item"); const isExpanded = await btn.getAttribute("aria-expanded"); if (isExpanded !== "true") { - await btn.click(); + await btn.click({ force: true }); } await expect(exportMenuItem).toBeVisible({ timeout: 10000 }); }; @@ -722,7 +722,7 @@ test.describe("Tenants Management", () => { await expect(page.getByTestId("tenant-import-menu-item")).toBeVisible(); const download = page.waitForEvent("download"); - await page.getByTestId("tenant-export-menu-item").click(); + await page.getByTestId("tenant-export-menu-item").click({ force: true }); const exportDownload = await download; expect(exportRequested).toBe(true); expect(exportDownload.suggestedFilename()).toBe("tenants.csv"); @@ -733,13 +733,15 @@ test.describe("Tenants Management", () => { page.getByTestId("tenant-export-with-ids-menu-item"), ).toBeVisible(); const exportWithIdsDownload = page.waitForEvent("download"); - await page.getByTestId("tenant-export-with-ids-menu-item").click(); + await page + .getByTestId("tenant-export-with-ids-menu-item") + .click({ force: true }); await exportWithIdsDownload; expect(exportUrl).toContain("includeIds=true"); await openDataManagementMenu(); const templateDownload = page.waitForEvent("download"); - await page.getByTestId("tenant-template-menu-item").click(); + await page.getByTestId("tenant-template-menu-item").click({ force: true }); const template = await templateDownload; expect(template.suggestedFilename()).toBe("tenant-import-template.csv");