=test_update_homework_tests_and_work_log
Some checks failed
CI / build-deploy (push) Has been cancelled
Some checks failed
CI / build-deploy (push) Has been cancelled
This commit is contained in:
27
tests/e2e/auth-business-flow.spec.ts
Normal file
27
tests/e2e/auth-business-flow.spec.ts
Normal file
@@ -0,0 +1,27 @@
|
||||
import { expect, test } from "@playwright/test"
|
||||
|
||||
test.describe("auth business flow", () => {
|
||||
test("register then login and reach protected area", async ({ page }) => {
|
||||
test.skip(!process.env.DATABASE_URL, "requires DATABASE_URL for write-flow verification")
|
||||
|
||||
const id = Date.now()
|
||||
const email = `e2e.user.${id}@example.com`
|
||||
const password = "e2e-pass-123456"
|
||||
|
||||
await page.goto("/register")
|
||||
await page.getByLabel("Full Name").fill("E2E User")
|
||||
await page.getByLabel("Email").fill(email)
|
||||
await page.getByLabel("Password").fill(password)
|
||||
await page.getByRole("button", { name: "Create Account" }).click()
|
||||
await expect(page).toHaveURL(/\/login(?:$|[/?#])/)
|
||||
|
||||
await page.getByLabel("Email").fill(email)
|
||||
await page.getByLabel("Password").fill(password)
|
||||
await page.getByRole("button", { name: "Sign In with Email" }).click()
|
||||
|
||||
await expect(page).toHaveURL(/\/(dashboard|student\/dashboard)(?:$|[/?#])/)
|
||||
const profileResponse = await page.goto("/profile")
|
||||
expect(profileResponse?.status() ?? 200).toBeLessThan(500)
|
||||
await expect(page).not.toHaveURL(/\/login(?:$|[/?#])/)
|
||||
})
|
||||
})
|
||||
75
tests/e2e/full-route-regression.spec.ts
Normal file
75
tests/e2e/full-route-regression.spec.ts
Normal file
@@ -0,0 +1,75 @@
|
||||
import fs from "node:fs"
|
||||
import path from "node:path"
|
||||
import { expect, test } from "@playwright/test"
|
||||
|
||||
const appRoot = path.resolve(__dirname, "../../src/app")
|
||||
const publicRoutes = new Set(["/", "/login", "/register"])
|
||||
|
||||
const toRoute = (filePath: string) => {
|
||||
const relative = path.relative(appRoot, filePath).replaceAll("\\", "/")
|
||||
const segments = relative
|
||||
.split("/")
|
||||
.slice(0, -1)
|
||||
.filter((segment) => !segment.startsWith("("))
|
||||
if (segments.some((segment) => segment.startsWith("["))) return null
|
||||
if (segments.length === 0) return "/"
|
||||
return `/${segments.join("/")}`
|
||||
}
|
||||
|
||||
const collectPageFiles = (dir: string): string[] => {
|
||||
const entries = fs.readdirSync(dir, { withFileTypes: true })
|
||||
return entries.flatMap((entry) => {
|
||||
const fullPath = path.join(dir, entry.name)
|
||||
if (entry.isDirectory()) return collectPageFiles(fullPath)
|
||||
return entry.name === "page.tsx" ? [fullPath] : []
|
||||
})
|
||||
}
|
||||
|
||||
const allStaticRoutes = Array.from(
|
||||
new Set(
|
||||
collectPageFiles(appRoot)
|
||||
.map((file) => toRoute(file))
|
||||
.filter((route): route is string => Boolean(route)),
|
||||
),
|
||||
).sort((a, b) => a.localeCompare(b))
|
||||
|
||||
const protectedRoutes = allStaticRoutes.filter((route) => !publicRoutes.has(route))
|
||||
|
||||
test.describe("full route regression", () => {
|
||||
test("route inventory is complete", async () => {
|
||||
expect(allStaticRoutes.length).toBeGreaterThanOrEqual(30)
|
||||
expect(allStaticRoutes).toContain("/admin/dashboard")
|
||||
expect(allStaticRoutes).toContain("/teacher/dashboard")
|
||||
expect(allStaticRoutes).toContain("/student/dashboard")
|
||||
expect(allStaticRoutes).toContain("/parent/dashboard")
|
||||
expect(allStaticRoutes).toContain("/settings")
|
||||
expect(allStaticRoutes).toContain("/profile")
|
||||
})
|
||||
|
||||
for (const route of publicRoutes) {
|
||||
test(`public route renders: ${route}`, async ({ page }) => {
|
||||
const response = await page.goto(route)
|
||||
expect(response?.status() ?? 200).toBeLessThan(500)
|
||||
await expect(page).not.toHaveURL(/\/500(?:$|[/?#])/)
|
||||
})
|
||||
}
|
||||
|
||||
for (const route of protectedRoutes) {
|
||||
test(`protected route guard: ${route}`, async ({ page }) => {
|
||||
const response = await page.goto(route)
|
||||
expect(response?.status() ?? 200).toBeLessThan(500)
|
||||
|
||||
const finalUrl = new URL(page.url())
|
||||
const finalPath = finalUrl.pathname
|
||||
expect(finalPath === route || finalPath === "/login").toBe(true)
|
||||
|
||||
if (finalPath === "/login") {
|
||||
const callbackUrl = finalUrl.searchParams.get("callbackUrl") ?? ""
|
||||
const normalizedCallback = callbackUrl.startsWith("http")
|
||||
? new URL(callbackUrl).pathname
|
||||
: callbackUrl
|
||||
expect(normalizedCallback === "" || normalizedCallback === route).toBe(true)
|
||||
}
|
||||
})
|
||||
}
|
||||
})
|
||||
20
tests/e2e/smoke-auth.spec.ts
Normal file
20
tests/e2e/smoke-auth.spec.ts
Normal file
@@ -0,0 +1,20 @@
|
||||
import { expect, test } from "@playwright/test"
|
||||
|
||||
test.describe("auth smoke", () => {
|
||||
test("login page renders required controls", async ({ page }) => {
|
||||
await page.goto("/login")
|
||||
await expect(page).toHaveTitle(/Login/i)
|
||||
await expect(page.getByLabel("Email")).toBeVisible()
|
||||
await expect(page.getByLabel("Password")).toBeVisible()
|
||||
await expect(page.getByRole("button", { name: "Sign In with Email" })).toBeVisible()
|
||||
})
|
||||
|
||||
test("register page renders required controls", async ({ page }) => {
|
||||
await page.goto("/register")
|
||||
await expect(page).toHaveTitle(/Register/i)
|
||||
await expect(page.getByLabel("Full Name")).toBeVisible()
|
||||
await expect(page.getByLabel("Email")).toBeVisible()
|
||||
await expect(page.getByLabel("Password")).toBeVisible()
|
||||
await expect(page.getByRole("button", { name: "Create Account" })).toBeVisible()
|
||||
})
|
||||
})
|
||||
Reference in New Issue
Block a user