chore: improve tooling, linting, testing, and CI
CI / check (push) Failing after 14s
Deploy / release (push) Skipped
Deploy / deploy (push) Successful in 2m38s

- Add LICENSE file (CC BY-NC-SA 4.0)
- Add .nvmrc pinning Node 22
- Add Renovate config with daily schedule and Gitea Actions workflow
- Reduce ESLint max-warnings from 1000 to 50
- Re-enable Biome a11y/security recommended rules
- Fix Biome lint issues (a11y, hook deps, SVG labels, checkbox semantics)
- Improve CI: run on pushes to feat/fix branches, add pnpm audit
- Add Vitest coverage with v8 provider and thresholds
- Add E2E tests (auth, admin, navigation specs)
- Add admin-maintenance server action test
- Install @vitest/coverage-v8
- Ignore coverage/ directory
This commit is contained in:
openhands committed 2026-07-27 17:03:09 +02:00
1 parent 0f5c190ab1
commit 423a33200e
28 files changed
+1016 -80

No files matched your search

+182
View File
@@ -0,0 +1,182 @@
import { beforeEach, describe, expect, it, vi } from "vitest";
const { mockUpsert, mockRequirePermission, mockReload, mockRevalidatePath } =
vi.hoisted(() => ({
mockUpsert: vi.fn(),
mockRequirePermission: vi.fn(),
mockReload: vi.fn(),
mockRevalidatePath: vi.fn(),
}));
vi.mock("@/lib/permissions", () => ({
PERMS: {
ADMIN_DASHBOARD: "admin.dashboard",
SETTINGS_VIEW: "admin.settings.view",
SETTINGS_EDIT: "admin.settings.edit",
},
}));
vi.mock("@/lib/prisma", () => ({
prisma: {
websiteSetting: { upsert: mockUpsert },
},
}));
vi.mock("@/lib/admin/guard", () => ({
requirePermission: mockRequirePermission,
}));
vi.mock("@/lib/services/site-settings", () => ({
siteSettings: { reload: mockReload },
}));
vi.mock("next/cache", () => ({
revalidatePath: mockRevalidatePath,
}));
import { saveMaintenance } from "./admin-maintenance";
beforeEach(() => {
vi.clearAllMocks();
});
describe("saveMaintenance", () => {
it("enables maintenance mode with message and min rank", async () => {
mockRequirePermission.mockResolvedValue({
id: 1,
rank: 7,
username: "admin",
});
const fd = new FormData();
fd.set("enabled", "on");
fd.set("message", "We will be back soon!");
fd.set("min_rank", "3");
await saveMaintenance(fd);
expect(mockRequirePermission).toHaveBeenCalled();
expect(mockUpsert).toHaveBeenCalledTimes(3);
expect(mockUpsert).toHaveBeenCalledWith(
expect.objectContaining({
where: { key: "maintenance_enabled" },
update: { value: "1" },
create: expect.objectContaining({
key: "maintenance_enabled",
value: "1",
}),
}),
);
expect(mockUpsert).toHaveBeenCalledWith(
expect.objectContaining({
where: { key: "maintenance_message" },
update: { value: "We will be back soon!" },
create: expect.objectContaining({
key: "maintenance_message",
value: "We will be back soon!",
}),
}),
);
expect(mockUpsert).toHaveBeenCalledWith(
expect.objectContaining({
where: { key: "min_maintenance_login_rank" },
update: { value: "3" },
create: expect.objectContaining({
key: "min_maintenance_login_rank",
value: "3",
}),
}),
);
expect(mockReload).toHaveBeenCalledOnce();
expect(mockRevalidatePath).toHaveBeenCalledWith("/admin/maintenance");
});
it("disables maintenance mode", async () => {
mockRequirePermission.mockResolvedValue({
id: 1,
rank: 7,
username: "admin",
});
const fd = new FormData();
fd.set("message", "");
fd.set("min_rank", "");
await saveMaintenance(fd);
expect(mockUpsert).toHaveBeenCalledWith(
expect.objectContaining({
where: { key: "maintenance_enabled" },
update: { value: "0" },
}),
);
expect(mockUpsert).toHaveBeenCalledWith(
expect.objectContaining({
where: { key: "min_maintenance_login_rank" },
update: { value: "5" },
}),
);
});
it("defaults min_rank to 5 when input is empty", async () => {
mockRequirePermission.mockResolvedValue({
id: 1,
rank: 7,
username: "admin",
});
const fd = new FormData();
fd.set("enabled", "on");
fd.set("message", "");
fd.set("min_rank", "");
await saveMaintenance(fd);
expect(mockUpsert).toHaveBeenCalledWith(
expect.objectContaining({
where: { key: "min_maintenance_login_rank" },
update: { value: "5" },
}),
);
});
it("defaults min_rank to 5 when input is negative", async () => {
mockRequirePermission.mockResolvedValue({
id: 1,
rank: 7,
username: "admin",
});
const fd = new FormData();
fd.set("enabled", "on");
fd.set("message", "");
fd.set("min_rank", "-1");
await saveMaintenance(fd);
expect(mockUpsert).toHaveBeenCalledWith(
expect.objectContaining({
where: { key: "min_maintenance_login_rank" },
update: { value: "5" },
}),
);
});
it("calls requirePermission with SETTINGS_EDIT", async () => {
mockRequirePermission.mockResolvedValue({
id: 1,
rank: 7,
username: "admin",
});
const fd = new FormData();
fd.set("message", "");
fd.set("min_rank", "");
await saveMaintenance(fd);
expect(mockRequirePermission).toHaveBeenCalledWith("admin.settings.edit");
});
});