Files
motovaultpro/backend/src/features/backup/README.md
Eric Gullickson 19ece562ed
All checks were successful
Deploy to Staging / Build Images (pull_request) Successful in 6m15s
Deploy to Staging / Deploy to Staging (pull_request) Successful in 28s
Deploy to Staging / Verify Staging (pull_request) Successful in 7s
Deploy to Staging / Notify Staging Ready (pull_request) Successful in 6s
Deploy to Staging / Notify Staging Failure (pull_request) Has been skipped
fix: Implement tiered backup retention classification (refs #6)
Replace per-schedule count-based retention with unified tiered classification.
Backups are now classified by timestamp into categories (hourly/daily/weekly/monthly)
and are only deleted when they exceed ALL applicable category quotas.

Changes:
- Add backup-classification.service.ts for timestamp-based classification
- Rewrite backup-retention.service.ts with tiered logic
- Add categories and expires_at columns to backup_history
- Add Expires column to desktop and mobile backup UI
- Add unit tests for classification logic (22 tests)

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-10 21:53:43 -06:00

5.7 KiB

Backup Feature

Complete backup and restore system for MotoVaultPro.

Overview

This feature provides:

  • Manual and scheduled backups of the PostgreSQL database and document files
  • Multiple backup schedules with individual retention policies
  • Restore functionality with safety backup creation
  • Email notifications on backup success/failure

Architecture

backup/
  api/                    # HTTP endpoints
    backup.routes.ts      # Route definitions
    backup.controller.ts  # Request handlers
    backup.validation.ts  # Zod schemas
  domain/                 # Business logic
    backup.types.ts       # TypeScript types and constants
    backup.service.ts     # Core backup operations
    backup-archive.service.ts      # Archive creation
    backup-restore.service.ts      # Restore operations
    backup-retention.service.ts    # Tiered retention enforcement
    backup-classification.service.ts  # Backup category classification
  data/                   # Data access
    backup.repository.ts  # Database queries
  jobs/                   # Scheduled jobs
    backup-scheduled.job.ts  # Scheduled backup execution
    backup-cleanup.job.ts    # Retention cleanup
  migrations/             # Database schema
    001_create_backup_tables.sql
    002_add_retention_categories.sql  # Tiered retention columns
  tests/                  # Test files
    unit/
      backup-classification.service.test.ts  # Classification tests

API Endpoints

All endpoints require admin authentication.

Backup Operations

Method Path Description
GET /api/admin/backups List backups with pagination
POST /api/admin/backups Create manual backup
GET /api/admin/backups/:id Get backup details
GET /api/admin/backups/:id/download Download backup file
DELETE /api/admin/backups/:id Delete backup
POST /api/admin/backups/upload Upload backup file

Restore Operations

Method Path Description
POST /api/admin/backups/:id/restore/preview Preview restore
POST /api/admin/backups/:id/restore Execute restore
GET /api/admin/backups/restore/status Get restore status

Schedule Operations

Method Path Description
GET /api/admin/backups/schedules List schedules
POST /api/admin/backups/schedules Create schedule
PUT /api/admin/backups/schedules/:id Update schedule
DELETE /api/admin/backups/schedules/:id Delete schedule
PATCH /api/admin/backups/schedules/:id/toggle Enable/disable

Settings

Method Path Description
GET /api/admin/backups/settings Get settings
PUT /api/admin/backups/settings Update settings

Backup Archive Format

Backups are .tar.gz archives containing:

motovaultpro_backup_YYYYMMDD_HHMMSS.tar.gz
  manifest.json           # Backup metadata
  database/
    motovaultpro.sql.gz   # Compressed PostgreSQL dump
  documents/
    <user_id>/            # User document files

Schedule Frequencies

Frequency Cron Default Time
hourly 0 * * * * Every hour
daily 0 3 * * * 3:00 AM
weekly 0 3 * * 0 Sunday 3:00 AM
monthly 0 3 1 * * 1st of month 3:00 AM

Database Tables

  • backup_schedules - Schedule configurations
  • backup_history - Backup operation records
  • backup_settings - Global settings

Storage

Backups are stored in /app/data/backups/ (mapped to ./data/backups/ on host).

Integration

Scheduler

Jobs are registered in backend/src/core/scheduler/index.ts:

  • Backup check: Every minute
  • Retention cleanup: Daily at 4 AM (also runs after each scheduled backup)

Distributed Locking

Scheduled backups use Redis distributed locking to prevent duplicate backups when multiple backend containers are running (blue-green deployments).

Lock behavior:

  • Lock key: backup:schedule:{schedule_id}
  • Lock TTL: 5 minutes (auto-release if container crashes)
  • Only one container creates the backup; others skip

Retention cleanup (tiered):

  • Runs immediately after each successful scheduled backup
  • Uses tiered classification: each backup can belong to multiple categories
  • A backup is only deleted when it exceeds ALL applicable category quotas
  • Also runs globally at 4 AM daily as a safety net

Tiered Retention System

Backups are classified by their creation timestamp into categories:

Category Qualification Retention Count
hourly All backups 8
daily First backup at midnight UTC 7
weekly First backup on Sunday at midnight UTC 4
monthly First backup on 1st of month at midnight UTC 12

Multi-category classification:

  • A backup can belong to multiple categories simultaneously
  • Example: Backup at midnight on Sunday, January 1st qualifies as: hourly + daily + weekly + monthly

Retention logic:

For each category (hourly, daily, weekly, monthly):
  1. Get all backups with this category
  2. Keep top N (sorted by started_at DESC)
  3. Add to protected set

A backup is deleted ONLY if it's NOT in the protected set
(i.e., exceeds quota for ALL its categories)

Expiration calculation:

  • Each backup's expires_at is calculated based on its longest retention period
  • Monthly backup: 12 months from creation
  • Weekly-only backup: 4 weeks from creation
  • Daily-only backup: 7 days from creation
  • Hourly-only backup: 8 hours from creation

See backend/src/core/scheduler/README.md for the distributed locking pattern.

Admin Routes

Routes are registered in backend/src/features/admin/api/admin.routes.ts.