diff --git a/doc/manual.rst b/doc/manual.rst index 10cd1282b..7a7221046 100644 --- a/doc/manual.rst +++ b/doc/manual.rst @@ -789,7 +789,7 @@ hours/days/weeks/months/years which have a snapshot, so those without a snapshot are ignored. All snapshots are evaluated counted against all matching keep-* counts. A -single snapshot on 30-09-2017 (Sun) will count as a daily, weekly and monthly. +single snapshot on 2017-09-30 (Sun) will count as a daily, weekly and monthly. Let's explain this with an example: Suppose you have only made a backup on each Sunday for 12 weeks. Then ``forget --keep-daily 4`` will keep @@ -803,8 +803,8 @@ Another example: Suppose you make daily backups for 100 years. Then ``forget --keep-daily 7 --keep-weekly 5 --keep-monthly 12 --keep-yearly 75`` will keep the most recent 7 daily snapshots, then 4 (remember, 7 dailies already include a week!) last-day-of-the-weeks and 11 or 12 -last-day-of-the-months. (11 or 12 depends if the 5 weeklies cross a month). -And ofcourse 75 last-day-of-the-year snapshots. All other snapshots are +last-day-of-the-months (11 or 12 depends if the 5 weeklies cross a month). +And finally 75 last-day-of-the-year snapshots. All other snapshots are removed. Autocompletion diff --git a/src/restic/snapshot_filter.go b/src/restic/snapshot_filter.go index 5461f18ff..450b2acc2 100644 --- a/src/restic/snapshot_filter.go +++ b/src/restic/snapshot_filter.go @@ -77,12 +77,9 @@ func y(d time.Time) int { return d.Year() } -var a int - -// always retuns a unique number for d. +// always returns a unique number for d. func always(d time.Time) int { - a++ - return a + return int(d.UnixNano()) } // ApplyPolicy returns the snapshots from list that are to be kept and removed diff --git a/src/restic/snapshot_filter_test.go b/src/restic/snapshot_filter_test.go index d8bbd4ec8..05e25fab6 100644 --- a/src/restic/snapshot_filter_test.go +++ b/src/restic/snapshot_filter_test.go @@ -57,7 +57,7 @@ var testExpireSnapshots = restic.Snapshots{ {Time: parseTimeUTC("2014-08-10 10:20:30")}, {Time: parseTimeUTC("2014-08-12 10:20:30")}, {Time: parseTimeUTC("2014-08-13 10:20:30")}, - {Time: parseTimeUTC("2014-08-13 10:20:30")}, + {Time: parseTimeUTC("2014-08-13 10:20:30.1")}, {Time: parseTimeUTC("2014-08-15 10:20:30")}, {Time: parseTimeUTC("2014-08-18 10:20:30")}, {Time: parseTimeUTC("2014-08-20 10:20:30")}, @@ -77,7 +77,7 @@ var testExpireSnapshots = restic.Snapshots{ {Time: parseTimeUTC("2014-11-10 10:20:30"), Tags: []string{"foo"}}, {Time: parseTimeUTC("2014-11-12 10:20:30"), Tags: []string{"foo"}}, {Time: parseTimeUTC("2014-11-13 10:20:30"), Tags: []string{"foo"}}, - {Time: parseTimeUTC("2014-11-13 10:20:30"), Tags: []string{"bar"}}, + {Time: parseTimeUTC("2014-11-13 10:20:30.1"), Tags: []string{"bar"}}, {Time: parseTimeUTC("2014-11-15 10:20:30"), Tags: []string{"foo", "bar"}}, {Time: parseTimeUTC("2014-11-18 10:20:30")}, {Time: parseTimeUTC("2014-11-20 10:20:30")}, @@ -97,7 +97,7 @@ var testExpireSnapshots = restic.Snapshots{ {Time: parseTimeUTC("2015-08-10 10:20:30")}, {Time: parseTimeUTC("2015-08-12 10:20:30")}, {Time: parseTimeUTC("2015-08-13 10:20:30")}, - {Time: parseTimeUTC("2015-08-13 10:20:30")}, + {Time: parseTimeUTC("2015-08-13 10:20:30.1")}, {Time: parseTimeUTC("2015-08-15 10:20:30")}, {Time: parseTimeUTC("2015-08-18 10:20:30")}, {Time: parseTimeUTC("2015-08-20 10:20:30")}, @@ -117,7 +117,7 @@ var testExpireSnapshots = restic.Snapshots{ {Time: parseTimeUTC("2015-11-10 10:20:30")}, {Time: parseTimeUTC("2015-11-12 10:20:30")}, {Time: parseTimeUTC("2015-11-13 10:20:30")}, - {Time: parseTimeUTC("2015-11-13 10:20:30")}, + {Time: parseTimeUTC("2015-11-13 10:20:30.1")}, {Time: parseTimeUTC("2015-11-15 10:20:30")}, {Time: parseTimeUTC("2015-11-18 10:20:30")}, {Time: parseTimeUTC("2015-11-20 10:20:30")}, @@ -169,53 +169,53 @@ var expireTests = []restic.ExpirePolicy{ func TestApplyPolicy(t *testing.T) { for i, p := range expireTests { - t.Run(fmt.Sprintf("%d", i), func(t *testing.T) { - keep, remove := restic.ApplyPolicy(testExpireSnapshots, p) + keep, remove := restic.ApplyPolicy(testExpireSnapshots, p) - t.Logf("test %d: returned keep %v, remove %v (of %v) expired snapshots for policy %v", - i, len(keep), len(remove), len(testExpireSnapshots), p) + t.Logf("test %d: returned keep %v, remove %v (of %v) expired snapshots for policy %v", + i, len(keep), len(remove), len(testExpireSnapshots), p) - if len(keep)+len(remove) != len(testExpireSnapshots) { - t.Errorf("test %d: len(keep)+len(remove) = %d != len(testExpireSnapshots) = %d", - i, len(keep)+len(remove), len(testExpireSnapshots)) - } + if len(keep)+len(remove) != len(testExpireSnapshots) { + t.Errorf("test %d: len(keep)+len(remove) = %d != len(testExpireSnapshots) = %d", + i, len(keep)+len(remove), len(testExpireSnapshots)) + } - if p.Sum() > 0 && len(keep) > p.Sum() { - t.Errorf("not enough snapshots removed: policy allows %v snapshots to remain, but ended up with %v", - p.Sum(), len(keep)) - } + if p.Sum() > 0 && len(keep) > p.Sum() { + t.Errorf("not enough snapshots removed: policy allows %v snapshots to remain, but ended up with %v", + p.Sum(), len(keep)) + } - for _, sn := range keep { - t.Logf("test %d: keep snapshot at %v %s\n", i, sn.Time, sn.Tags) - } - for _, sn := range remove { - t.Logf("test %d: forget snapshot at %v %s\n", i, sn.Time, sn.Tags) - } + for _, sn := range keep { + t.Logf("test %d: keep snapshot at %v %s\n", i, sn.Time, sn.Tags) + } + for _, sn := range remove { + t.Logf("test %d: forget snapshot at %v %s\n", i, sn.Time, sn.Tags) + } - goldenFilename := filepath.Join("testdata", fmt.Sprintf("policy_keep_snapshots_%d", i)) + goldenFilename := filepath.Join("testdata", fmt.Sprintf("policy_keep_snapshots_%d", i)) - if *updateGoldenFiles { - buf, err := json.MarshalIndent(keep, "", " ") - if err != nil { - t.Fatalf("error marshaling result: %v", err) - } - - if err = ioutil.WriteFile(goldenFilename, buf, 0644); err != nil { - t.Fatalf("unable to update golden file: %v", err) - } - } - - buf, err := ioutil.ReadFile(goldenFilename) + if *updateGoldenFiles { + buf, err := json.MarshalIndent(keep, "", " ") if err != nil { - t.Fatalf("error loading golden file %v: %v", goldenFilename, err) + t.Fatalf("error marshaling result: %v", err) } - var want restic.Snapshots - err = json.Unmarshal(buf, &want) - - if !reflect.DeepEqual(keep, want) { - t.Fatalf("test %v: wrong result, want:\n %v\ngot:\n %v", i, want, keep) + if err = ioutil.WriteFile(goldenFilename, buf, 0644); err != nil { + t.Fatalf("unable to update golden file: %v", err) } - }) + } + + buf, err := ioutil.ReadFile(goldenFilename) + if err != nil { + t.Errorf("error loading golden file %v: %v", goldenFilename, err) + continue + } + + var want restic.Snapshots + err = json.Unmarshal(buf, &want) + + if !reflect.DeepEqual(keep, want) { + t.Errorf("test %v: wrong result, want:\n %v\ngot:\n %v", i, want, keep) + continue + } } } diff --git a/src/restic/testdata/policy_keep_snapshots_0 b/src/restic/testdata/policy_keep_snapshots_0 index 952f8c02e..159d55d0c 100644 --- a/src/restic/testdata/policy_keep_snapshots_0 +++ b/src/restic/testdata/policy_keep_snapshots_0 @@ -120,7 +120,7 @@ "paths": null }, { - "time": "2015-11-13T10:20:30Z", + "time": "2015-11-13T10:20:30.1Z", "tree": null, "paths": null }, @@ -270,7 +270,7 @@ "paths": null }, { - "time": "2015-08-13T10:20:30Z", + "time": "2015-08-13T10:20:30.1Z", "tree": null, "paths": null }, @@ -324,7 +324,7 @@ ] }, { - "time": "2014-11-13T10:20:30Z", + "time": "2014-11-13T10:20:30.1Z", "tree": null, "paths": null, "tags": [ @@ -519,7 +519,7 @@ "paths": null }, { - "time": "2014-08-13T10:20:30Z", + "time": "2014-08-13T10:20:30.1Z", "tree": null, "paths": null }, @@ -543,4 +543,4 @@ "tree": null, "paths": null } -] +] \ No newline at end of file diff --git a/src/restic/testdata/policy_keep_snapshots_10 b/src/restic/testdata/policy_keep_snapshots_10 index e2d61b68b..ca08ff08a 100644 --- a/src/restic/testdata/policy_keep_snapshots_10 +++ b/src/restic/testdata/policy_keep_snapshots_10 @@ -49,4 +49,4 @@ "tree": null, "paths": null } -] +] \ No newline at end of file diff --git a/src/restic/testdata/policy_keep_snapshots_13 b/src/restic/testdata/policy_keep_snapshots_13 index abf4ed809..57b4ab846 100644 --- a/src/restic/testdata/policy_keep_snapshots_13 +++ b/src/restic/testdata/policy_keep_snapshots_13 @@ -19,4 +19,4 @@ "tree": null, "paths": null } -] +] \ No newline at end of file diff --git a/src/restic/testdata/policy_keep_snapshots_15 b/src/restic/testdata/policy_keep_snapshots_15 index 51bed0e6e..c8fcf1e20 100644 --- a/src/restic/testdata/policy_keep_snapshots_15 +++ b/src/restic/testdata/policy_keep_snapshots_15 @@ -34,4 +34,4 @@ "tree": null, "paths": null } -] +] \ No newline at end of file diff --git a/src/restic/testdata/policy_keep_snapshots_17 b/src/restic/testdata/policy_keep_snapshots_17 index 8eb4ce6f8..1398e524f 100644 --- a/src/restic/testdata/policy_keep_snapshots_17 +++ b/src/restic/testdata/policy_keep_snapshots_17 @@ -49,4 +49,4 @@ "tree": null, "paths": null } -] +] \ No newline at end of file diff --git a/src/restic/testdata/policy_keep_snapshots_18 b/src/restic/testdata/policy_keep_snapshots_18 index caf2b746e..3ca6727a0 100644 --- a/src/restic/testdata/policy_keep_snapshots_18 +++ b/src/restic/testdata/policy_keep_snapshots_18 @@ -120,4 +120,4 @@ "foo" ] } -] +] \ No newline at end of file diff --git a/src/restic/testdata/policy_keep_snapshots_19 b/src/restic/testdata/policy_keep_snapshots_19 index 177e8b400..af86beb84 100644 --- a/src/restic/testdata/policy_keep_snapshots_19 +++ b/src/restic/testdata/policy_keep_snapshots_19 @@ -8,4 +8,4 @@ "bar" ] } -] +] \ No newline at end of file diff --git a/src/restic/testdata/policy_keep_snapshots_3 b/src/restic/testdata/policy_keep_snapshots_3 index 952f8c02e..159d55d0c 100644 --- a/src/restic/testdata/policy_keep_snapshots_3 +++ b/src/restic/testdata/policy_keep_snapshots_3 @@ -120,7 +120,7 @@ "paths": null }, { - "time": "2015-11-13T10:20:30Z", + "time": "2015-11-13T10:20:30.1Z", "tree": null, "paths": null }, @@ -270,7 +270,7 @@ "paths": null }, { - "time": "2015-08-13T10:20:30Z", + "time": "2015-08-13T10:20:30.1Z", "tree": null, "paths": null }, @@ -324,7 +324,7 @@ ] }, { - "time": "2014-11-13T10:20:30Z", + "time": "2014-11-13T10:20:30.1Z", "tree": null, "paths": null, "tags": [ @@ -519,7 +519,7 @@ "paths": null }, { - "time": "2014-08-13T10:20:30Z", + "time": "2014-08-13T10:20:30.1Z", "tree": null, "paths": null }, @@ -543,4 +543,4 @@ "tree": null, "paths": null } -] +] \ No newline at end of file diff --git a/src/restic/testdata/policy_keep_snapshots_4 b/src/restic/testdata/policy_keep_snapshots_4 index 952f8c02e..159d55d0c 100644 --- a/src/restic/testdata/policy_keep_snapshots_4 +++ b/src/restic/testdata/policy_keep_snapshots_4 @@ -120,7 +120,7 @@ "paths": null }, { - "time": "2015-11-13T10:20:30Z", + "time": "2015-11-13T10:20:30.1Z", "tree": null, "paths": null }, @@ -270,7 +270,7 @@ "paths": null }, { - "time": "2015-08-13T10:20:30Z", + "time": "2015-08-13T10:20:30.1Z", "tree": null, "paths": null }, @@ -324,7 +324,7 @@ ] }, { - "time": "2014-11-13T10:20:30Z", + "time": "2014-11-13T10:20:30.1Z", "tree": null, "paths": null, "tags": [ @@ -519,7 +519,7 @@ "paths": null }, { - "time": "2014-08-13T10:20:30Z", + "time": "2014-08-13T10:20:30.1Z", "tree": null, "paths": null }, @@ -543,4 +543,4 @@ "tree": null, "paths": null } -] +] \ No newline at end of file diff --git a/src/restic/testdata/policy_keep_snapshots_5 b/src/restic/testdata/policy_keep_snapshots_5 index 42ed6051a..dcc09e864 100644 --- a/src/restic/testdata/policy_keep_snapshots_5 +++ b/src/restic/testdata/policy_keep_snapshots_5 @@ -95,7 +95,7 @@ "paths": null }, { - "time": "2015-11-13T10:20:30Z", + "time": "2015-11-13T10:20:30.1Z", "tree": null, "paths": null } diff --git a/src/restic/testdata/policy_keep_snapshots_8 b/src/restic/testdata/policy_keep_snapshots_8 index b0a64d691..a9656bd3c 100644 --- a/src/restic/testdata/policy_keep_snapshots_8 +++ b/src/restic/testdata/policy_keep_snapshots_8 @@ -75,7 +75,7 @@ "paths": null }, { - "time": "2015-11-13T10:20:30Z", + "time": "2015-11-13T10:20:30.1Z", "tree": null, "paths": null }, diff --git a/src/restic/testdata/policy_keep_snapshots_9 b/src/restic/testdata/policy_keep_snapshots_9 index 776816b08..c491b089f 100644 --- a/src/restic/testdata/policy_keep_snapshots_9 +++ b/src/restic/testdata/policy_keep_snapshots_9 @@ -29,4 +29,4 @@ "tree": null, "paths": null } -] +] \ No newline at end of file