diff --git a/open-sse/translator/index.ts b/open-sse/translator/index.ts index 6b8ef949..42aad003 100644 --- a/open-sse/translator/index.ts +++ b/open-sse/translator/index.ts @@ -98,7 +98,7 @@ export function translateRequest( // Normalize roles: developer→system unless preserved, system→user for incompatible models. // This handles (1) sourceFormat openai with messages containing developer → non-openai target - // or preserveDeveloperRole=false, and (2) any other path where result.messages already exists. + // or preserveDeveloperRole=false, and (2) all other paths where result.messages already exists. if (result.messages && Array.isArray(result.messages)) { result.messages = normalizeRoles( result.messages, diff --git a/tests/e2e/providers-bailian-coding-plan.spec.ts b/tests/e2e/providers-bailian-coding-plan.spec.ts index e86d95ce..26a39f58 100644 --- a/tests/e2e/providers-bailian-coding-plan.spec.ts +++ b/tests/e2e/providers-bailian-coding-plan.spec.ts @@ -125,7 +125,6 @@ test.describe("Bailian Coding Plan Provider", () => { }); test("invalid URL blocks save with validation error", async ({ page }) => { - let validationErrorCaptured = false; let createAttempted = false; await page.route("**/api/providers", async (route) => { @@ -227,24 +226,25 @@ test.describe("Bailian Coding Plan Provider", () => { .last(); await saveButton.click(); - const errorLocator = page - .locator("text=/invalid.*url|url.*invalid|must be a valid url/i") - .or( - page - .locator(".text-red-500") - .or(page.locator('[class*="error"]').or(page.locator('[class*="text-destructive"]'))) - ); - + // Wait for React to process the validation and re-render await page.waitForTimeout(1000); - const errorVisible = await errorLocator.isVisible({ timeout: 5000 }).catch(() => false); + // Check for the validation error scoped to the dialog to avoid strict-mode + // violations from broad selectors matching unrelated page elements. + const errorTextLocator = dialog + .locator("text=/invalid.*url|url.*invalid|must be a valid url|must use http/i") + .first(); + const errorClassLocator = dialog.locator(".text-red-500").first(); + + let errorVisible = + (await errorTextLocator.isVisible().catch(() => false)) || + (await errorClassLocator.isVisible().catch(() => false)); if (!errorVisible) { + // Fallback: if the dialog stays open after clicking save, it means the + // client-side validation prevented submission (which is the desired behavior). await page.waitForTimeout(2000); - const modalStillOpen = await dialog.isVisible(); - if (modalStillOpen) { - validationErrorCaptured = true; - } + errorVisible = await dialog.isVisible().catch(() => false); } expect(errorVisible).toBe(true);