import { ref } from 'vue' import type { AuditLogEntry, AuditLogFilters } from '~/shared/types' import type { HydraCollection } from '~/shared/utils/api' import { onAuthSessionCleared } from '~/shared/stores/auth' /** * Cache module-level : evite un double-fetch si la page et le composant * Timeline demandent la meme page simultanement. Volontairement minimaliste : * on ne cache que le dernier resultat, pas un LRU par filtre — un CRM interne * n'en a pas besoin et le cache complexe complique le reset. * * Un logout / 401 doit purger ce cache : on s'enregistre au callback * `onAuthSessionCleared` expose par auth.ts. */ const lastCollection = ref | null>(null) function resetAuditLog(): void { lastCollection.value = null } // Auto-enregistrement singleton : si la session est invalidee (401, // logout) le cache est purge automatiquement, evitant qu'un autre user // connecte ensuite ne voit des donnees residuelles. onAuthSessionCleared(resetAuditLog) /** * Traduit le modele front (camelCase) en query params API Platform * (snake_case, avec la syntaxe performed_at[after] / [before]). * * @returns objet plat directement consommable par `useApi().get(url, query)`. */ function buildQuery(filters: AuditLogFilters | undefined): Record { const query: Record = {} if (!filters) return query if (filters.entityType) query.entity_type = filters.entityType if (filters.entityId) query.entity_id = filters.entityId if (filters.action) query.action = filters.action if (filters.performedBy) query.performed_by = filters.performedBy if (filters.performedAtAfter) query['performed_at[after]'] = filters.performedAtAfter if (filters.performedAtBefore) query['performed_at[before]'] = filters.performedAtBefore if (filters.page) query.page = filters.page return query } /** * Composable partage entre la page globale d'audit (admin) et le composant * Timeline. Expose des methodes de lecture + une fonction `resetAuditLog()` * pour purger le cache (conforme a la regle CLAUDE.md sur les composables * singletons, cf. `useSidebar.resetSidebar`). */ export function useAuditLog() { const api = useApi() async function fetchLogs(filters?: AuditLogFilters): Promise> { const data = await api.get>( '/audit-logs', buildQuery(filters), { toast: false }, ) lastCollection.value = data return data } async function fetchLogById(id: string): Promise { return api.get(`/audit-logs/${id}`, {}, { toast: false }) } async function fetchEntityLogs( entityType: string, entityId: string | number, page: number = 1, ): Promise> { return fetchLogs({ entityType, entityId: String(entityId), page, }) } return { lastCollection, fetchLogs, fetchLogById, fetchEntityLogs, resetAuditLog, } }