/** * portal/auditui/api.mjs — 활동·감사 기록 화면(§24.2). 현재 그룹의 기록만, 비밀값 없음(lib/audit 가 기록 시 redact). * 필터: 행동(action 접두어)·대상 종류·기간. 삭제 불가 기록(immutable)과 자동 작업을 표시한다. */ import { requireGroup } from '../auth/guard.mjs'; import { listAudit } from '../../lib/audit.mjs'; import { t } from '../../lib/i18n.mjs'; export async function register(app, deps) { app.get('/activity', (ctx) => { requireGroup(ctx); return ctx.html(deps.shell(ctx, { title: t('activity.title'), nav: null, crumbs: [{ label: t('activity.title') }], body: `
${deps.statePanel('loading')}
` })); }); app.get('/api/audit', (ctx) => { requireGroup(ctx); const items = listAudit(deps.store, { groupId: ctx.group.id, action: ctx.query.action || undefined, subjectType: ctx.query.subjectType || undefined, since: ctx.query.since ? ctx.query.since + 'T00:00:00.000Z' : undefined, until: ctx.query.until ? ctx.query.until + 'T23:59:59.999Z' : undefined, limit: Number(ctx.query.limit || 200) }).map((a) => ({ id: a.id, at: a.at, actor: a.actor_label || a.actor_type, actorType: a.actor_type, automatic: !!a.automatic || a.actor_type === 'system', action: a.action, outcome: a.outcome, subjectType: a.subject_type, subjectId: a.subject_id, immutable: !!a.immutable, detail: a.detail })); return { ok: true, items }; }); }