Introducing Filename Timestamps in retentions

We’ve added a new time source to retentions: we can now determine backup age from timestamps embedded in file and directory names.

With --age-type 'filename=<format>', we can apply our existing retention rules using the date recorded in the backup name.

📅 A backup date that travels with our files

Many backup workflows already produce names such as:

Plaintext
backup-2026-11-09_020000.tar.gz
backup-2026-11-10_020000.tar.gz
backup-2026-11-11_020000.tar.gz

These names carry information about when the backups were created. Filesystem timestamps may change when we copy, migrate, extract, or restore those backups.

By reading the date from the filename, we can keep our retention decisions tied to the recorded backup date—even after moving the files between systems.

🛠️ One option, familiar retention rules

We select the new time source and specify the timestamp format:

Bash
retentions /data/backups 'backup-*.tar.gz' \
  --age-type 'filename=%Y-%m-%d_%H%M%S' \
  --days 7 --weeks 4 --months 12 \
  --dry-run --verbose INFO

For backup-2026-11-11_020000.tar.gz, this extracts 11 November 2026 at 02:00:00.

We describe the timestamp using Python’s date/time format codes. The filename pattern selects our backup files; the format describes the date and time within their names.

Our existing retention options continue to work with this source, including calendar-based rules, --last, and limits on file count, total size, or maximum age. In the example, --dry-run lets us inspect the decisions without deleting anything.

🕒 Matching our naming conventions

We can adapt the format to different backup names:

Timestamp in the name Format
2026-11-11 %Y-%m-%d
20261111 %Y%m%d
11.11.2026_020000 %d.%m.%Y_%H%M%S
2026-11-11T020000+0000 %Y-%m-%dT%H%M%S%z

Dates without an explicit timezone use local time. With %z, we can read numeric UTC offsets such as +0000. Dates without a time of day use midnight.

📁 Using timestamps in folder mode

We’ve also integrated the new source into folder mode. Depending on our configuration, we can use:

  • The timestamp embedded in the directory’s own name.
  • The timestamp embedded in a specified file’s name inside that directory.
  • The youngest or oldest timestamp found in recursively contained filenames.

This supports both individual backup archives and backup directories containing multiple files.

🔎 Handling names without a valid date

We exclude names without an interpretable timestamp from sorting and normal retention decisions. At WARN verbosity or higher, we report which names could not be evaluated, while processing continues for valid entries.

Explicit companion-deletion rules retain their existing behavior, so associated checksum or metadata files can still be removed alongside their backups.

We can start with a dry run against an existing backup directory and review exactly how the dates in our filenames translate into retention decisions.

📚 date and time format codes

You can find the complete reference for Python’s date and time format codes in the official datetime documentation.