Files
ctms/frontend/src/views/admin/Users.test.ts
T
2026-06-11 09:09:17 +08:00

112 lines
4.9 KiB
TypeScript

import { describe, expect, it } from "vitest";
import { readFileSync } from "node:fs";
import { resolve } from "node:path";
const readUsersView = () => readFileSync(resolve(__dirname, "./Users.vue"), "utf8");
const readUserForm = () => readFileSync(resolve(__dirname, "./UserForm.vue"), "utf8");
const readLocale = () => readFileSync(resolve(__dirname, "../../locales/zh-CN.ts"), "utf8");
describe("Admin users table labels", () => {
it("shows clinical_department as 科室 in the account management table", () => {
const viewSource = readUsersView();
const localeSource = readLocale();
expect(viewSource).toContain(':label="TEXT.modules.adminUsers.clinicalDepartmentLabel"');
expect(viewSource).not.toContain(':label="TEXT.common.fields.clinicalDepartment"');
expect(localeSource).toContain('clinicalDepartmentLabel: "科室"');
});
});
describe("Admin users table layout", () => {
it("uses a wider name column, even remaining columns, and compact icon actions", () => {
const viewSource = readUsersView();
expect(viewSource).toContain('table-layout="fixed"');
expect(viewSource).toContain(':label="TEXT.common.fields.name" width="360"');
expect(viewSource).not.toContain('width="20%"');
expect(viewSource).not.toContain('width="180"');
expect(viewSource).not.toContain('width="160"');
expect(viewSource).not.toContain('width="100"');
expect(viewSource).not.toContain('fixed="right"');
expect(viewSource).toContain('class="action-btn"');
expect(viewSource).toContain("width: 28px;");
expect(viewSource).toContain("gap: 4px;");
});
it("shows names without avatar icons in the account management table", () => {
const viewSource = readUsersView();
expect(viewSource).not.toContain("user-avatar");
expect(viewSource).not.toContain("getInitials(scope.row.full_name)");
expect(viewSource).not.toContain("linear-gradient(135deg, #3f8f6b, #2d7a5a)");
});
});
describe("Admin users summary header", () => {
it("keeps the management summary header compact", () => {
const viewSource = readUsersView();
expect(viewSource).toContain("padding: 10px 16px;");
expect(viewSource).toContain("padding: 9px 12px;");
expect(viewSource).toContain("width: 32px;");
expect(viewSource).toContain("height: 32px;");
expect(viewSource).toContain("font-size: 20px;");
expect(viewSource).toContain("font-size: 11px;");
});
});
describe("Admin users filters", () => {
it("applies keyword automatically and status filters from the first page", () => {
const viewSource = readUsersView();
expect(viewSource).toContain("@keyup.enter=\"applyFilters\"");
expect(viewSource).toContain("@change=\"applyFilters\"");
expect(viewSource).not.toContain("@click=\"applyFilters\"");
expect(viewSource).not.toContain(":icon=\"Refresh\"");
expect(viewSource).not.toContain("Refresh } from");
expect(viewSource).toContain("watch(searchKeyword, () => {");
expect(viewSource).toContain("scheduleKeywordSearch();");
expect(viewSource).toContain("keywordSearchTimer = setTimeout(() => {");
expect(viewSource).toContain("}, 300);");
expect(viewSource).toContain("page.value = 1");
expect(viewSource).toContain("keyword: searchKeyword.value || undefined");
expect(viewSource).toContain("status: statusFilter.value || undefined");
});
});
describe("Admin user form autocomplete", () => {
it("prevents browser credential autofill when creating a user", () => {
const formSource = readUserForm();
expect(formSource).toContain('autocomplete="off"');
expect(formSource).toContain('name="ctms-create-initial-password"');
expect(formSource).toContain('autocomplete="new-password"');
expect(formSource).not.toContain("current_password");
expect(formSource).not.toContain("confirmPassword");
expect(formSource).not.toContain("TEXT.modules.profile.currentPassword");
expect(formSource).not.toContain("TEXT.modules.profile.confirmPassword");
});
});
describe("Admin user create form password", () => {
it("requires an initial password before creating an account", () => {
const formSource = readUserForm();
expect(formSource).toContain('v-if="!user" :label="TEXT.modules.adminUsers.passwordInitial" prop="password"');
expect(formSource).toContain("TEXT.modules.adminUsers.passwordInitialRequired");
expect(formSource).toContain("/^(?=.*[A-Za-z])(?=.*\\d).{8,}$/");
});
});
describe("Admin user edit form defaults", () => {
it("hydrates the selected user immediately when the dialog is mounted open", () => {
const formSource = readUserForm();
expect(formSource).toContain("immediate: true");
expect(formSource).not.toContain("current_password");
expect(formSource).not.toContain("confirmPassword");
expect(formSource).not.toContain("TEXT.modules.profile.currentPassword");
expect(formSource).not.toContain("TEXT.modules.profile.confirmPassword");
});
});