Show that scheduled deletion actually happened
Every run of the scheduled retention deletion leaves a record of what it deleted, what it held back and whether it failed, so a privacy notice calls a period enforced only when the records show it.
- What it is
- Guarantee — a guarantee that holds on its own.
- What it does
- A record for every run, including failed ones. Each run and each bound resource ends as completed, deferred by the per-run limit (a backlog being worked through), failed, or skipped with a reason. A failed run leaves a record too, so an operator can see when deletion stopped working.
- What you decide
- Nothing to enable: every run of the retention deletion writes its records. Collect them into the application's evidence when you prepare documents or an assurance review.
- Where it stops
- Files and audit logs are removed by their own mechanisms, which write no such record, so those classes read as declared rather than enforced.

The scheduled retention deletion writes one record per run for every resource it is responsible for: how many expired records it deleted, how many it did not delete because a legal hold covers them, under which declared period, and how the run ended. The records are the evidence that a declared retention period is being enforced, rather than only configured.
The problem it solves
Storage limitation is a principle an operator has to be able to demonstrate. A job that deletes on schedule and leaves no durable trace cannot demonstrate anything: a successful run’s result lives only as long as the job record, and a job that quietly stopped working looks the same as one that had nothing to do. A privacy notice that calls a period enforced because a resource is configured for it is stating a hope.
What it does
A record for every run, including failed ones. Each run and each bound resource ends as completed, deferred by the per-run limit (a backlog being worked through), failed, or skipped with a reason. A failed run leaves a record too, so an operator can see when deletion stopped working.
Counts and times, never content. No record names a deleted row or carries a value, so the evidence outlives the data without copying it. The records themselves are kept as long as the audit trail.
Readable by an evidence reader. The records of the runs in a time window are available through the application’s evidence door, under the same access rules and audit as the other evidence the application gives an assurance reviewer.
Documents say what the records show. For each declared class, a privacy notice states one of three things: enforced (recent runs deleted what was due or are working through a bounded backlog), declared (a period exists but the records do not show it enforced), or failing (the latest run of a bound resource failed).
What you decide
Nothing to enable: every run of the retention deletion writes its records. Collect them into the application’s evidence when you prepare documents or an assurance review.
Selected from retention-enforcement-records.shared.schemas.ts;
the documentation comments, the record’s identifiers and its other optional fields are omitted.
sweptAt: z.date().isDBIndexed().isSummaryField(),
retentionClass: z.enum(DataRetentionClass).systemEnum('DataRetentionClass').isDBIndexed().isSummaryField(),
resourceType: z.string().min(1).isDBIndexed().isSummaryField(),
startPoint: z.enum(RetentionStartPoint).systemEnum('RetentionStartPoint'),
// …
retentionDaysApplied: z.number().int().min(0).optional(),
// …
deletedCount: z.number().int().min(0),
// …
heldSkippedCount: z.number().int().min(0).optional(),
// …
reachedRunCeiling: z.boolean(),
outcome: z.enum(RetentionEnforcementOutcome).systemEnum('RetentionEnforcementOutcome').isDBIndexed().isSummaryField(),
A record names a resource type, never a row, and carries only counts and instants: the period the run applied, how many expired records it deleted, how many a legal hold kept, whether it stopped at its per-run limit, and how it ended. A held-back count that is absent means no hold check ran for that resource in that run, which is not the same as zero.
Limits
Files and audit logs are removed by their own mechanisms, which write no such record, so those classes read as declared rather than enforced.