diff --git a/changelog/unreleased/issue-4568 b/changelog/unreleased/issue-4568 index 4d44809c5..fedf373ea 100644 --- a/changelog/unreleased/issue-4568 +++ b/changelog/unreleased/issue-4568 @@ -8,6 +8,10 @@ The `forget` command now fails with an error if all snapshots in a snapshot group would be deleted. This prevents the above example from deleting all snapshots. +It is possible to temporarily disable the new check by setting the environment variable +`RESTIC_FEATURES=safe-forget-keep-tags=false`. Note that this feature flag +will be removed in the next minor restic version. + https://github.com/restic/restic/issues/4568 https://github.com/restic/restic/pull/4764 https://forum.restic.net/t/delete-all-snapshots-in-one-command-is-this-feature-intentional/6923/3 diff --git a/cmd/restic/cmd_forget.go b/cmd/restic/cmd_forget.go index 328b28271..9c40b1d09 100644 --- a/cmd/restic/cmd_forget.go +++ b/cmd/restic/cmd_forget.go @@ -8,6 +8,7 @@ import ( "strconv" "github.com/restic/restic/internal/errors" + "github.com/restic/restic/internal/feature" "github.com/restic/restic/internal/restic" "github.com/restic/restic/internal/ui/termstatus" "github.com/spf13/cobra" @@ -258,7 +259,7 @@ func runForget(ctx context.Context, opts ForgetOptions, pruneOptions PruneOption keep, remove, reasons := restic.ApplyPolicy(snapshotGroup, policy) - if !policy.Empty() && len(keep) == 0 { + if feature.Flag.Enabled(feature.SafeForgetKeepTags) && !policy.Empty() && len(keep) == 0 { return fmt.Errorf("refusing to delete last snapshot of snapshot group \"%v\"", key.String()) } if len(keep) != 0 && !gopts.Quiet && !gopts.JSON { diff --git a/internal/feature/registry.go b/internal/feature/registry.go index ac4105140..74d8a2f61 100644 --- a/internal/feature/registry.go +++ b/internal/feature/registry.go @@ -9,6 +9,7 @@ const ( DeprecateLegacyIndex FlagName = "deprecate-legacy-index" DeprecateS3LegacyLayout FlagName = "deprecate-s3-legacy-layout" DeviceIDForHardlinks FlagName = "device-id-for-hardlinks" + SafeForgetKeepTags FlagName = "safe-forget-keep-tags" ) func init() { @@ -17,5 +18,6 @@ func init() { DeprecateLegacyIndex: {Type: Beta, Description: "disable support for index format used by restic 0.1.0. Use `restic repair index` to update the index if necessary."}, DeprecateS3LegacyLayout: {Type: Beta, Description: "disable support for S3 legacy layout used up to restic 0.7.0. Use `RESTIC_FEATURES=deprecate-s3-legacy-layout=false restic migrate s3_layout` to migrate your S3 repository if necessary."}, DeviceIDForHardlinks: {Type: Alpha, Description: "store deviceID only for hardlinks to reduce metadata changes for example when using btrfs subvolumes. Will be removed in a future restic version after repository format 3 is available"}, + SafeForgetKeepTags: {Type: Beta, Description: "prevent deleting all snapshots if the tag passed to `forget --keep-tags tagname` does not exist"}, }) }