restic backup --dry-run: ver qué se copiaría sin tocar el repositorio
tras --dry-run el repositorio seguía con 1 snapshot y los mismos bytes en data/; la estimación (5,003 MiB) coincidió con lo añadido por el backup real (5,003 MiB).
Este artículo no contiene enlaces de afiliado.
Antes de cambiar una lista de exclusiones o lanzar un backup grande, restic backup --dry-run dice qué haría sin escribir nada. Se probó qué muestra con cada nivel de detalle y si de verdad deja el repositorio igual.
Condiciones: restic 0.16.4 en Linux arm64, repositorio local, un fichero aleatorio de 20 MiB ya copiado, luego un fichero de texto modificado y otro nuevo de 5 MiB. Contraseña desechable. No se probó con repositorios remotos. Script completo al final.
Qué se observó
| Paso | Resultado |
|---|---|
--dry-run |
"Would add to the repository: 5.003 MiB (5.002 MiB stored)"; Files: 1 new, 1 changed, 1 unmodified |
| Estado tras el dry-run | 1 snapshot, mismos bytes en data/ que antes |
| Backup real | "Added to the repository: 5.003 MiB (5.002 MiB stored)"; 2 snapshots |
La estimación coincidió con lo añadido después, en esta prueba con datos aleatorios incompresibles. Con datos que cambian entre ejecuciones no hay garantía.
Qué detalle da cada nivel
- Sin
-v: solo el resumen de ficheros y bytes. -v: añade el recuento de blobs de datos y de árbol, pero no los nombres de fichero.-vv: una línea por fichero connew,modifiedounchanged, más los directorios padre. Es lo útil para ver si una exclusión hace lo que esperas. Aunque sea dry-run, restic escribe "saved in ..." en esas líneas; no se guardó nada.
El dry-run sí abre el repositorio, lo bloquea y carga el índice (se ve en la salida con -v), así que necesita la contraseña y acceso al repositorio. No sirve para comprobar un backup sin acceso al repo.
Relacionado: excluir node_modules y cachés y códigos de salida de restic.
Script completo
#!/bin/bash
# restic backup --dry-run: what it reports and whether the repository changes. Usage: test-restic-dry-run.sh WORKDIR
W=$1; rm -rf "$W"; mkdir -p "$W/datos"
export RESTIC_PASSWORD=prueba-desechable
R="$W/repo"; restic init -r "$R" >/dev/null
head -c 20M /dev/urandom > "$W/datos/grande.bin"; echo uno > "$W/datos/a.txt"
restic -r "$R" backup "$W/datos" --quiet
size() { du -sb "$R/data" | cut -f1; }
snaps() { restic -r "$R" snapshots --json | python3 -c 'import sys,json;print(len(json.load(sys.stdin)))'; }
echo "== antes: snapshots=$(snaps) data_bytes=$(size)"
echo dos > "$W/datos/a.txt"; head -c 5M /dev/urandom > "$W/datos/nuevo.bin"
echo "== backup --dry-run -vv"; restic -r "$R" backup "$W/datos" --dry-run -vv 2>&1 | grep -E "^(new|modified|unchanged|Would)"; echo "-- resumen (-v)"; restic -r "$R" backup "$W/datos" --dry-run -v 2>&1 | grep -vE "^(repository|using parent|scan|Files:|Dirs:|Added)" ; restic -r "$R" backup "$W/datos" --dry-run 2>&1 | grep -E "^(Files:|Added)"
echo "== tras dry-run: snapshots=$(snaps) data_bytes=$(size)"
echo "== backup real"; restic -r "$R" backup "$W/datos" 2>&1 | grep -E "^(Files:|Added)"
echo "== tras real: snapshots=$(snaps) data_bytes=$(size)"
echo "== dry-run con exclusion"; restic -r "$R" backup "$W/datos" --dry-run -v --exclude '*.bin' 2>&1 | grep -E "^(unchanged|modified|new|Files:)"