Audit logging is written early, never read, and then urgently needed during an incident or a dispute — at which point teams discover it recorded that "a record was updated" without saying by whom, to what, or from where.

The four fields

  • Actor: the authenticated identity, not a display name that can change.
  • Action: a stable machine-readable string such as case.deleted, not free prose.
  • Target: type and identifier of what was affected.
  • Time: ISO 8601, in UTC, always.

Add the source address and enough detail to make the entry meaningful on its own — a status transition, the reason given, the record's human-readable reference. The test is whether someone reading only the log, months later, understands what happened.

What to log first

Prioritise privileged and destructive actions: permission changes, password resets initiated by staff, data exports, deletions, access to sensitive records, and configuration changes. Those are what investigations and disputes turn on. Logging every read is usually noise that buries the entries that matter.

Append-only, and outliving the record

Audit entries must not be editable by the application that writes them, and must survive the deletion of what they describe. An audit trail for a deleted record that is deleted along with it answers nothing. Deletion is precisely the event you need evidence of afterwards.

Make it queryable

Index on actor, target and time. Give staff a read-only view so questions can be answered without a database session. And decide retention deliberately — long enough for disputes and investigations, bounded enough to respect data protection obligations, and documented either way.

Protect it

Audit logs contain who accessed what, which is sensitive. Restrict access, log access to the logs themselves for the most sensitive systems, and be careful never to write credentials, tokens or full personal data into an audit record.