Replace @services/ → codebase/features/, @applications/@lilith → @projects/@lilith, docker-compose.dev.yml → docker-compose.yml, docker-compose.prod.yml → docker-compose.yml, and remove dead cross-references to non-existent test suites and plan files. Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
9.1 KiB
Backup Infrastructure Setup
Automated setup for the complete backup infrastructure using the @lilith/restic-* and @lilith/vault-* packages.
Overview
This setup orchestrator reads a declarative config file and executes the entire infrastructure setup:
- Phase 1: Deploy restic REST server on black (10.0.0.11)
- Phase 2: Configure restic clients on workstations (apricot)
- Phase 3: Setup vault symlinks on workstations (apricot)
- Phase 4: Configure encrypted backups on macbook
Files
backup-infrastructure.config.yaml- Declarative infrastructure configsetup-backup-infrastructure.ts- Orchestration scriptsetup-backup-infrastructure.sh- Bash wrapper (convenience)
Quick Start
1. Install Dependencies
# Install the packages (from forge.nasty.sh)
pnpm add @lilith/restic-setup-server \
@lilith/restic-setup-client \
@lilith/vault-setup-client \
@lilith/vault-setup-backup
# Install system packages
sudo dnf install restic # On Fedora/apricot
brew install restic # On macOS
2. Configure Infrastructure
Edit backup-infrastructure.config.yaml:
restic_server:
host: 10.0.0.11 # black's IP
hostname: black
port: 8000
restic_clients:
- hostname: apricot # Workstation name
server_url: http://10.0.0.11:8000
vault_backup:
hostname: macbook # MacBook for encrypted backups
source: ~/.vault/
destination: ~/Documents/VaultBackups/
3. Run Setup
Full setup (all phases):
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts
Dry run (see what would happen):
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts --dry-run
Run specific phase:
# Deploy server only
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts --phase server
# Configure clients only
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts --phase client
# Setup vault only
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts --phase vault
# Setup encrypted backups only
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts --phase backup
Run for specific host:
# Setup only apricot
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts --host apricot
# Setup only macbook
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts --host macbook
Usage Scenarios
Scenario 1: Fresh Setup (All Machines)
# 1. Run from any machine with SSH access to black
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts
# 2. Script will:
# - Generate restic password
# - Deploy server to black
# - Configure clients on apricot (via SSH or run locally)
# - Setup vault on apricot
# - Setup encrypted backups on macbook
# - Prompt for master password
Scenario 2: Server Already Deployed (Clients Only)
# Skip server deployment, setup clients only
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts --phase client
# Or setup vault only
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts --phase vault
Scenario 3: Add New Workstation
# 1. Edit config: Add new client to restic_clients and vault_clients
# 2. Run on new machine:
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts \
--phase client \
--host new-workstation
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts \
--phase vault \
--host new-workstation
Scenario 4: Dry Run (Test Before Executing)
# See what would happen without making changes
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts --dry-run
Credentials Management
Restic Password
Generated (default):
credentials:
restic_password_source: generate # Auto-generate secure password
Prompt user:
credentials:
restic_password_source: prompt # Ask user to enter password
Load from vault (not yet implemented):
credentials:
restic_password_source: vault # Load from vault
Master Password (Encrypted Backups)
Prompt user:
credentials:
master_password_source: prompt # User must enter password
Load from vault (default):
credentials:
master_password_source: vault # Load from vault/hosts/workstations.txt
When using vault source, the script loads the password from vault/hosts/workstations.txt using the vault_backup.hostname (macbook). This should be the macbook user login password.
Setup: Add macbook credentials to vault before running with vault source:
## MACBOOK
Username: [your_username]
Password: [your_login_password]
Hostname: macbook
Notes: Password used for encrypted vault backups
This password is DIFFERENT from restic password. It's used for AES-256-GCM encryption of local vault backups.
Verification
After setup completes, verify each component:
Verify Restic Server (black)
# SSH to black
ssh lilith@10.0.0.11
# Check container
docker ps | grep restic
# Check logs
docker logs restic-rest-server
# Test API
curl http://localhost:8000/
Verify Restic Client (apricot)
# On apricot
systemctl --user list-timers | grep restic
systemctl --user status restic-backup-code.timer
journalctl --user -u restic-backup-code.service -n 50
# List snapshots
export RESTIC_PASSWORD="..."
restic -r rest:http://10.0.0.11:8000/apricot-code snapshots
Verify Vault (apricot)
# On apricot
ls -la ~/.vault
ls ~/.vault/
# Keychain (macOS)
security find-generic-password -s restic-backup -a lilith-platform-workstations -w
Verify Encrypted Backups (macbook)
# On macbook
ls -lh ~/Documents/VaultBackups/
# Test restore
npx @lilith/vault-setup-backup restore \
--backup ~/Documents/VaultBackups/vault-backup-*.enc \
--destination /tmp/test \
--password "YOUR_MASTER_PASSWORD"
ls /tmp/test
rm -rf /tmp/test
Troubleshooting
Server Deployment Fails
# Check SSH access
ssh lilith@10.0.0.11 "docker ps"
# Check paths exist
ssh lilith@10.0.0.11 "ls -la /bigdisk/"
Client Setup Fails
# Check restic binary
which restic
restic version
# Check server is accessible
curl http://10.0.0.11:8000/
Vault Symlink Fails
# Check project path
ls ~/Code/@projects/@lilith/lilith-platform/vault/
# Remove broken symlink
rm ~/.vault
# Re-run setup
pnpm tsx deployments/provisioning/setup-backup-infrastructure.ts --phase vault
Encrypted Backup Fails
# Check source exists
ls ~/.vault/
# Check destination writable
mkdir -p ~/Documents/VaultBackups
touch ~/Documents/VaultBackups/test && rm ~/Documents/VaultBackups/test
Architecture
┌─────────────────────────────────────────────┐
│ backup-infrastructure.config.yaml │
│ (Declarative Infrastructure Config) │
└─────────────────┬───────────────────────────┘
│
v
┌─────────────────────────────────────────────┐
│ setup-backup-infrastructure.ts │
│ (Orchestrator) │
│ │
│ 1. Read config │
│ 2. Handle credentials │
│ 3. Execute phases │
│ 4. Verify results │
└──┬──────────┬──────────┬──────────┬─────────┘
│ │ │ │
v v v v
┌──────┐ ┌──────┐ ┌──────┐ ┌──────┐
│restic│ │restic│ │vault │ │vault │
│setup │ │setup │ │setup │ │setup │
│server│ │client│ │client│ │backup│
└──────┘ └──────┘ └──────┘ └──────┘
│ │ │ │
v v v v
black apricot apricot macbook
Security Notes
- Restic password: Generated securely (32 chars), stored in Keychain
- Master password: User-chosen, NOT stored anywhere (memory only)
- SSH: Key-based auth to black (not password)
- Vault: Contains no plaintext secrets (all encrypted)
- Backups: Encrypted with AES-256-GCM before storage
Next Steps
After successful setup:
- Save passwords: Store restic password and master password in password manager
- Test restores: Monthly, verify backups can be restored
- Monitor: Check
journalctl --user -u restic-backup-code.serviceweekly - Update: Keep packages updated (
pnpm update @lilith/restic-*)
See Also
- Package docs:
~/Code/@packages/@infrastructure/*/README.md - Platform docs:
CLAUDE.md(Infrastructure Setup Packages section) - Manual setup: See approved plan in
~/.claude/plans/(if not deleted)