Files
familienarchiv/frontend/src/routes/admin/layout.server.spec.ts
Marcel 567612761d refactor: move lib-root files to lib/shared/ and finalize domain structure
- Move api.server.ts, errors.ts, types.ts, utils.ts, relativeTime.ts to lib/shared/
- Move person relationship components to lib/person/relationship/
- Move Stammbaum components to lib/person/genealogy/
- Move HelpPopover to lib/shared/primitives/
- Update all import paths across routes, specs, and lib files
- Update vi.mock() paths in server-project test files
- Remove now-empty legacy directories (components/, hooks/, server/, etc.)
- Update vite.config.ts coverage include paths for new structure
- Update frontend/CLAUDE.md to reflect domain-based lib/ layout

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-05 14:53:31 +02:00

79 lines
2.5 KiB
TypeScript

import { describe, expect, it, vi, beforeEach } from 'vitest';
import { load } from './+layout.server';
vi.mock('$lib/shared/api.server', () => ({ createApiClient: vi.fn() }));
import { createApiClient } from '$lib/shared/api.server';
function mockApi(users: unknown[], groups: unknown[], tags: unknown[]) {
vi.mocked(createApiClient).mockReturnValue({
GET: vi
.fn()
.mockResolvedValueOnce({ response: { ok: true }, data: users })
.mockResolvedValueOnce({ response: { ok: true }, data: groups })
.mockResolvedValueOnce({ response: { ok: true }, data: tags })
} as ReturnType<typeof createApiClient>);
}
const adminUser = {
groups: [{ permissions: ['ADMIN', 'ADMIN_USER', 'ADMIN_TAG', 'ADMIN_PERMISSION'] }]
};
const tagAdminUser = { groups: [{ permissions: ['ADMIN_TAG'] }] };
const noPermUser = { groups: [{ permissions: ['READ_ALL'] }] };
beforeEach(() => vi.clearAllMocks());
describe('admin layout load — permission check', () => {
it('throws 403 when user has no admin permission', async () => {
await expect(
load({ fetch: vi.fn() as unknown as typeof fetch, locals: { user: noPermUser } })
).rejects.toMatchObject({ status: 403 });
});
it('throws 403 when user is undefined', async () => {
await expect(
load({ fetch: vi.fn() as unknown as typeof fetch, locals: { user: undefined } })
).rejects.toMatchObject({ status: 403 });
});
it('throws 403 when user has no groups', async () => {
await expect(
load({ fetch: vi.fn() as unknown as typeof fetch, locals: { user: { groups: [] } } })
).rejects.toMatchObject({ status: 403 });
});
it('allows access for a user with ADMIN_TAG only', async () => {
mockApi([], [], []);
await expect(
load({ fetch: vi.fn() as unknown as typeof fetch, locals: { user: tagAdminUser } })
).resolves.toBeDefined();
});
it('returns entity counts and permission flags for a full admin', async () => {
mockApi(
[{ id: 'u1' }, { id: 'u2' }],
[{ id: 'g1' }],
[{ id: 't1' }, { id: 't2' }, { id: 't3' }]
);
const mockFetch = vi.fn().mockResolvedValue({
ok: true,
json: async () => [{ id: 'i1' }, { id: 'i2' }]
});
const result = await load({
fetch: mockFetch as unknown as typeof fetch,
locals: { user: adminUser }
});
expect(result.userCount).toBe(2);
expect(result.groupCount).toBe(1);
expect(result.tagCount).toBe(3);
expect(result.inviteCount).toBe(2);
expect(result.canManageUsers).toBe(true);
expect(result.canManageTags).toBe(true);
expect(result.canManagePermissions).toBe(true);
expect(result.canRunMaintenance).toBe(true);
});
});