Add snapshot_delete_dir option to remove directories from snapshots#648
Add snapshot_delete_dir option to remove directories from snapshots#648mnikulin wants to merge 2 commits into
Conversation
|
Don't you want to put the snapshot in a temporary directory first, then do atomic rename? |
This seems to add quite a bit of complexity compared to the original snapshot creation flow before this PR. Also, mv is not very easy to constrain precisely in sudoers: paths can be limited with regexes, but reliably expressing "only rename this expected temporary snapshot to its matching final name" would likely require a dedicated wrapper. |
|
Deleting directories doesn't provide enough power anyway. You want something at least as powerful as rsync pattern files, but really, to just punt on the whole thing to a script, which can then be as simple as deleting directories or as complex as reading Borg- or rsync-style pattern descriptions |
|
A script-based approach may be a good solution for a more general feature, but I am not sure it is in the spirit of btrbk. It is also a broader design with different trade-offs than what I am trying to solve here. My goal was even simpler: get a backup without a few configurable directories. This is what I have been missing in btrbk for years, and even this already runs into some limitations of btrfs snapshots. I do not need rsync- or Borg-style pattern handling for my use case. |
|
You want to omit a few directories. Others want to omit a few files. Others might want to do size-based cleaning or something. You can't make everyone happy with a static approach, and I can't see an a priori reason to prefer directory exclusion over other kinds. |
Summary
Adds a new configuration option
snapshot_delete_dirthat allows specifying a list of directories to be deleted inside newly created snapshots before they are set read-only.When
snapshot_delete_diris configured, btrbk:btrfs property set ro trueIf any deletion fails, the snapshot is removed and the subvolume section is skipped (same error handling as a failed snapshot creation).
Configuration Example
Motivation
This is an implementation of the approach discussed in issue #258 — a simple, explicit list of directories to exclude from snapshots, without complex include/exclude glob patterns.
This also partially addresses #238: users who want backups to contain only certain parts of a subvolume can now delete the unwanted directories from snapshots after creation.
Security
The path argument is validated with
check_file(..., relative => 1, sanitize => 1)to prevent path traversal attacks (e.g. a misconfigured../../../../home).When using
backend_remote btrfs-progs-sudo, btrbk invokes commands viasudo -n. Forsnapshot_delete_dir, two additional commands are executed on the source/snapshot host:sudo -n btrfs property set <snapshot_path> ro truesudo -n rm -rf <snapshot_path>/<dir>To follow the principle of least privilege, you can restrict
rm -rfin/etc/sudoersto the exact snapshot directory prefix instead of allowing arbitrary paths:This limits
rm -rfto paths matching the snapshot naming pattern (e.g./mnt/snapshots/home/user.20260627T0000+0300), preventing accidental or malicious deletion of unrelated paths.Implementation Notes
btrfs property set ro trueis used to make the snapshot read-only after cleanup. This approach preserves theparent_uuidrelationship, enabling incremental send/receive to work correctly.ssh_filter_btrbk.shis updated to allowbtrfs property set <path> ro trueandrm -rf <path>when--sourceor--snapshotmode is used.global,volume, andsubvolumecontext and can be specified multiple times.