import { afterEach, describe, expect, it, vi } from 'vitest' import { adminToken, buildTestApp } from './helpers.js' import { startHousekeepingJob } from '../src/services/housekeeping.js' let app: Awaited> | undefined afterEach(async () => { vi.useRealTimers() await app?.close() app = undefined }) describe('directory/users', () => { it('отдаёт только id/email/name и ограничивает 50', async () => { app = await buildTestApp() const token = await adminToken(app) for (let i = 0; i < 55; i++) { app.sqlite .prepare( `INSERT INTO users (id,email,name,password_hash,is_admin,disabled,created_at,updated_at) VALUES (?,?,?,?,0,0,'t','t')`, ) .run(`id${i}`, `u${i}@t.io`, `U${i}`, 'hash') } const res = await app.inject({ method: 'GET', url: '/api/v1/directory/users', headers: { authorization: `Bearer ${token}` }, }) expect(res.statusCode).toBe(200) const body = res.json() as Array> expect(body).toHaveLength(50) expect(Object.keys(body[0]!).sort()).toEqual(['email', 'id', 'name']) expect(res.body).not.toContain('hash') const q = await app.inject({ method: 'GET', url: '/api/v1/directory/users?q=U54', headers: { authorization: `Bearer ${token}` }, }) expect((q.json() as unknown[]).length).toBe(1) }) }) describe('ingest audit', () => { const ev = (i: number) => ({ event_id: `ev-${i}`, source_app: 'dns', action: 'dns.test', severity: 'info', summary: 'x', }) it('принимает пачку одной транзакцией и считает дубликаты', async () => { app = await buildTestApp() const post = (events: unknown[]) => app!.inject({ method: 'POST', url: '/api/v1/ingest/audit', headers: { authorization: 'Bearer dev-audit-ingest-secret' }, payload: { events }, }) const first = await post([ev(1), ev(2), ev(3)]) expect(first.json()).toEqual({ accepted: 3, duplicates: 0 }) const second = await post([ev(3), ev(4)]) expect(second.json()).toEqual({ accepted: 1, duplicates: 1 }) }) }) describe('housekeeping job', () => { it('удаляет устаревшие сессии по таймеру и останавливается', async () => { vi.useFakeTimers() app = await buildTestApp() app.sqlite .prepare( `INSERT INTO users (id,email,name,password_hash,is_admin,disabled,created_at,updated_at) VALUES ('uh','h@t.io','H','x',0,0,'t','t')`, ) .run() app.sqlite .prepare( `INSERT INTO refresh_sessions (id,user_id,token_hash,expires_at,created_at) VALUES ('old','uh','h','2000-01-01T00:00:00.000Z','t')`, ) .run() const stop = startHousekeepingJob(app) await vi.advanceTimersByTimeAsync(31_000) const left = app.sqlite .prepare(`SELECT COUNT(*) c FROM refresh_sessions WHERE id='old'`) .get() expect(left).toEqual({ c: 0 }) stop() expect(vi.getTimerCount()).toBe(0) }) })