mirror of https://github.com/digint/btrbk
btrbk: add options "{snapshot,target,archive}_qgroup_destroy": destroy qgroups whenever a subvolume is deleted
Btrfs does not destroy qgroups when subvolumes are deleted (see https://bugzilla.kernel.org/show_bug.cgi?id=91751). As a workaround for this, btrbk can be configured to always destroy the corresponding default qgroup "0/<subvol-id>" whenever a subvolume (snapshot, backup or archive) is deleted. Added configuration options: - snapshot_qgroup_destroy - target_qgroup_destroy - archive_qgroup_destroypull/204/head
parent
6cb98700d8
commit
e9a517f161
|
@ -12,6 +12,8 @@ btrbk-current
|
||||||
* Change raw backup format (sidecar file instead of uuid in file).
|
* Change raw backup format (sidecar file instead of uuid in file).
|
||||||
* Honor target_preserve for raw targets (delete raw targets).
|
* Honor target_preserve for raw targets (delete raw targets).
|
||||||
* Add symmetric encryption for raw targets (close #157).
|
* Add symmetric encryption for raw targets (close #157).
|
||||||
|
* Add "{snapshot,target,archive}_qgroup_destroy" configuration
|
||||||
|
options (close #49, #189).
|
||||||
* Do not run in "perl taint mode" by default: remove "perl -T" in
|
* Do not run in "perl taint mode" by default: remove "perl -T" in
|
||||||
hashbang; hardcode $PATH only if taint mode is enabled.
|
hashbang; hardcode $PATH only if taint mode is enabled.
|
||||||
* Remove "duration" column from transaction_log/transaction_syslog.
|
* Remove "duration" column from transaction_log/transaction_syslog.
|
||||||
|
|
44
btrbk
44
btrbk
|
@ -124,6 +124,10 @@ my %config_options = (
|
||||||
backend_local => { default => undef, accept => [ "no", "btrfs-progs", "btrfs-progs-btrbk", "btrfs-progs-sudo" ] },
|
backend_local => { default => undef, accept => [ "no", "btrfs-progs", "btrfs-progs-btrbk", "btrfs-progs-sudo" ] },
|
||||||
backend_remote => { default => undef, accept => [ "no", "btrfs-progs", "btrfs-progs-btrbk", "btrfs-progs-sudo" ] },
|
backend_remote => { default => undef, accept => [ "no", "btrfs-progs", "btrfs-progs-btrbk", "btrfs-progs-sudo" ] },
|
||||||
|
|
||||||
|
snapshot_qgroup_destroy => { default => undef, accept => [ "yes", "no" ], context => [ "root", "volume", "subvolume" ] },
|
||||||
|
target_qgroup_destroy => { default => undef, accept => [ "yes", "no" ] },
|
||||||
|
archive_qgroup_destroy => { default => undef, accept => [ "yes", "no" ], context => [ "root" ] },
|
||||||
|
|
||||||
# deprecated options
|
# deprecated options
|
||||||
btrfs_progs_compat => { default => undef, accept => [ "yes", "no" ],
|
btrfs_progs_compat => { default => undef, accept => [ "yes", "no" ],
|
||||||
deprecated => { DEFAULT => { ABORT => 1, warn => 'This feature has been dropped in btrbk-v0.23.0. Please update to newest btrfs-progs, AT LEAST >= $BTRFS_PROGS_MIN' } } },
|
deprecated => { DEFAULT => { ABORT => 1, warn => 'This feature has been dropped in btrbk-v0.23.0. Please update to newest btrfs-progs, AT LEAST >= $BTRFS_PROGS_MIN' } } },
|
||||||
|
@ -214,6 +218,7 @@ my %backend_cmd_map = (
|
||||||
"btrfs subvolume delete" => [ "btrfs-subvolume-delete" ],
|
"btrfs subvolume delete" => [ "btrfs-subvolume-delete" ],
|
||||||
"btrfs send" => [ "btrfs-send" ],
|
"btrfs send" => [ "btrfs-send" ],
|
||||||
"btrfs receive" => [ "btrfs-receive" ],
|
"btrfs receive" => [ "btrfs-receive" ],
|
||||||
|
"btrfs qgroup destroy" => [ "btrfs-qgroup-destroy" ],
|
||||||
},
|
},
|
||||||
"btrfs-progs-sudo" => { "btrfs subvolume list" => [ "sudo", "-n", "btrfs", "subvolume", "list" ],
|
"btrfs-progs-sudo" => { "btrfs subvolume list" => [ "sudo", "-n", "btrfs", "subvolume", "list" ],
|
||||||
"btrfs subvolume show" => [ "sudo", "-n", "btrfs", "subvolume", "show" ],
|
"btrfs subvolume show" => [ "sudo", "-n", "btrfs", "subvolume", "show" ],
|
||||||
|
@ -221,6 +226,7 @@ my %backend_cmd_map = (
|
||||||
"btrfs subvolume delete" => [ "sudo", "-n", "btrfs", "subvolume", "delete" ],
|
"btrfs subvolume delete" => [ "sudo", "-n", "btrfs", "subvolume", "delete" ],
|
||||||
"btrfs send" => [ "sudo", "-n", "btrfs", "send" ],
|
"btrfs send" => [ "sudo", "-n", "btrfs", "send" ],
|
||||||
"btrfs receive" => [ "sudo", "-n", "btrfs", "receive" ],
|
"btrfs receive" => [ "sudo", "-n", "btrfs", "receive" ],
|
||||||
|
"btrfs qgroup destroy" => [ "sudo", "-n", "btrfs", "qgroup", "destroy" ],
|
||||||
},
|
},
|
||||||
);
|
);
|
||||||
|
|
||||||
|
@ -1280,6 +1286,33 @@ sub btrfs_subvolume_delete($@)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
sub btrfs_qgroup_destroy($@)
|
||||||
|
{
|
||||||
|
my $vol = shift // die;
|
||||||
|
my %opts = @_;
|
||||||
|
my $vol_id = $vol->{node}{id};
|
||||||
|
unless($vol_id) {
|
||||||
|
ERROR "Unknown subvolume_id for: $vol->{PRINT}";
|
||||||
|
return undef;
|
||||||
|
}
|
||||||
|
my $path = $vol->{PATH} // die;
|
||||||
|
my $qgroup_id = "0/$vol_id";
|
||||||
|
INFO "[qgroup-destroy] qgroup_id: $qgroup_id";
|
||||||
|
INFO "[qgroup-destroy] subvolume: $vol->{PRINT}";
|
||||||
|
start_transaction($opts{type} // "qgroup_destroy",
|
||||||
|
vinfo_prefixed_keys("target", $vol));
|
||||||
|
my $ret = run_cmd(cmd => vinfo_cmd($vol, "btrfs qgroup destroy", $qgroup_id, { unsafe => $path }),
|
||||||
|
rsh => vinfo_rsh($vol),
|
||||||
|
);
|
||||||
|
end_transaction($opts{type} // "qgroup_destroy", defined($ret));
|
||||||
|
unless(defined($ret)) {
|
||||||
|
ERROR "Failed to destroy qgroup \"$qgroup_id\" for subvolume: $vol->{PRINT}";
|
||||||
|
return undef;
|
||||||
|
}
|
||||||
|
return $vol;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
sub btrfs_send_receive($$$$)
|
sub btrfs_send_receive($$$$)
|
||||||
{
|
{
|
||||||
my $snapshot = shift || die;
|
my $snapshot = shift || die;
|
||||||
|
@ -3512,6 +3545,11 @@ sub macro_delete($$$$$;@)
|
||||||
preserve_date_in_future => 1,
|
preserve_date_in_future => 1,
|
||||||
);
|
);
|
||||||
|
|
||||||
|
if($delete_options{qgroup}->{destroy}) {
|
||||||
|
# NOTE: we do not abort on qgroup destroy errors
|
||||||
|
btrfs_qgroup_destroy($_, %{$delete_options{qgroup}}) foreach(@$delete);
|
||||||
|
}
|
||||||
|
|
||||||
my @delete_success = btrfs_subvolume_delete($delete, %delete_options);
|
my @delete_success = btrfs_subvolume_delete($delete, %delete_options);
|
||||||
$subvol_dir .= '/' if($subvol_dir ne "");
|
$subvol_dir .= '/' if($subvol_dir ne "");
|
||||||
INFO "Deleted " . scalar(@delete_success) . " subvolumes in: $root_subvol->{PRINT}/$subvol_dir$subvol_basename.*";
|
INFO "Deleted " . scalar(@delete_success) . " subvolumes in: $root_subvol->{PRINT}/$subvol_dir$subvol_basename.*";
|
||||||
|
@ -4605,6 +4643,8 @@ MAIN:
|
||||||
},
|
},
|
||||||
commit => config_key($droot, "btrfs_commit_delete"),
|
commit => config_key($droot, "btrfs_commit_delete"),
|
||||||
type => "delete_archive",
|
type => "delete_archive",
|
||||||
|
qgroup => { destroy => config_key($droot, "archive_qgroup_destroy"),
|
||||||
|
type => "qgroup_destroy_archive" },
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -5751,6 +5791,8 @@ MAIN:
|
||||||
},
|
},
|
||||||
commit => config_key($droot, "btrfs_commit_delete"),
|
commit => config_key($droot, "btrfs_commit_delete"),
|
||||||
type => "delete_target",
|
type => "delete_target",
|
||||||
|
qgroup => { destroy => config_key($droot, "target_qgroup_destroy"),
|
||||||
|
type => "qgroup_destroy_target" },
|
||||||
))
|
))
|
||||||
{
|
{
|
||||||
$target_aborted = 1;
|
$target_aborted = 1;
|
||||||
|
@ -5780,6 +5822,8 @@ MAIN:
|
||||||
},
|
},
|
||||||
commit => config_key($svol, "btrfs_commit_delete"),
|
commit => config_key($svol, "btrfs_commit_delete"),
|
||||||
type => "delete_snapshot",
|
type => "delete_snapshot",
|
||||||
|
qgroup => { destroy => config_key($svol, "snapshot_qgroup_destroy"),
|
||||||
|
type => "qgroup_destroy_snapshot" },
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -320,6 +320,19 @@ For convenience, it is also possible to set \fIbackend_local\fR or
|
||||||
local or remote sources/targets (e.g. "backend_remote
|
local or remote sources/targets (e.g. "backend_remote
|
||||||
btrfs-progs-btrbk").
|
btrfs-progs-btrbk").
|
||||||
.RE
|
.RE
|
||||||
|
.PP
|
||||||
|
\fBsnapshot_qgroup_destroy\fR yes|no \fI*experimental*\fR
|
||||||
|
.PD 0
|
||||||
|
.PP
|
||||||
|
\fBtarget_qgroup_destroy\fR yes|no \fI*experimental*\fR
|
||||||
|
.PP
|
||||||
|
\fBarchive_qgroup_destroy\fR yes|no \fI*experimental*\fR
|
||||||
|
.PD
|
||||||
|
.RS 4
|
||||||
|
Whenever a subvolume is deleted, also destroy corresponding default
|
||||||
|
qgroup "0/<subvol-id>". Only useful if you have enabled btrfs quota
|
||||||
|
support. See also: <https://bugzilla.kernel.org/show_bug.cgi?id=91751>
|
||||||
|
.RE
|
||||||
.SH RETENTION POLICY
|
.SH RETENTION POLICY
|
||||||
btrbk uses separate retention policies for snapshots and backups,
|
btrbk uses separate retention policies for snapshots and backups,
|
||||||
which are defined by the \fIsnapshot_preserve_min\fR,
|
which are defined by the \fIsnapshot_preserve_min\fR,
|
||||||
|
|
Loading…
Reference in New Issue