import { describe, it, expect } from 'vitest' // Pure helpers extracted (conceptually) from dashboard logic — tested here as standalone functions function computeCapaOnTimeRate( capas: Array<{ due_date: string; completed_at: string | null; verified_at: string | null }> ): number | null { if (capas.length === 0) return null const onTime = capas.filter(c => { const due = new Date(c.due_date) const done = c.verified_at ? new Date(c.verified_at) : c.completed_at ? new Date(c.completed_at) : null return done !== null && done <= due }) return Math.round((onTime.length / capas.length) * 100) } function classifyIndicators(incidents: Array<{ incident_type: string }>) { const leading = incidents.filter(i => ['hazard', 'near_miss'].includes(i.incident_type)).length const lagging = incidents.filter(i => i.incident_type === 'injury').length return { leading, lagging } } describe('CAPA on-time rate', () => { it('returns null for empty list', () => { expect(computeCapaOnTimeRate([])).toBeNull() }) it('returns 100% when all CAPAs completed on time', () => { const capas = [ { due_date: '2026-07-10', completed_at: '2026-07-09', verified_at: null }, { due_date: '2026-07-10', completed_at: null, verified_at: '2026-07-08' }, ] expect(computeCapaOnTimeRate(capas)).toBe(100) }) it('returns 50% when half are late', () => { const capas = [ { due_date: '2026-07-10', completed_at: '2026-07-09', verified_at: null }, { due_date: '2026-07-10', completed_at: '2026-07-12', verified_at: null }, ] expect(computeCapaOnTimeRate(capas)).toBe(50) }) it('returns 0% when all CAPAs are overdue', () => { const capas = [ { due_date: '2026-07-10', completed_at: '2026-07-15', verified_at: null }, ] expect(computeCapaOnTimeRate(capas)).toBe(0) }) }) describe('leading vs lagging indicators', () => { it('counts hazard and near_miss as leading', () => { const incidents = [ { incident_type: 'hazard' }, { incident_type: 'near_miss' }, { incident_type: 'injury' }, { incident_type: 'fire' }, ] const { leading, lagging } = classifyIndicators(incidents) expect(leading).toBe(2) expect(lagging).toBe(1) }) })