From 6cf4b815583cc5b19e12eda46bab910b4ad1d529 Mon Sep 17 00:00:00 2001 From: Alexander Neumann Date: Fri, 19 Aug 2016 20:50:52 +0200 Subject: [PATCH] Add functions to filter snapshots --- src/restic/snapshot.go | 3 +- src/restic/snapshot_filter.go | 195 +++++++++ src/restic/snapshot_filter_test.go | 262 ++++++++++++ src/restic/testdata/expired_snapshots_0 | 497 +++++++++++++++++++++++ src/restic/testdata/expired_snapshots_1 | 52 +++ src/restic/testdata/expired_snapshots_10 | 12 + src/restic/testdata/expired_snapshots_11 | 22 + src/restic/testdata/expired_snapshots_12 | 37 ++ src/restic/testdata/expired_snapshots_13 | 32 ++ src/restic/testdata/expired_snapshots_14 | 52 +++ src/restic/testdata/expired_snapshots_15 | 17 + src/restic/testdata/expired_snapshots_16 | 72 ++++ src/restic/testdata/expired_snapshots_2 | 77 ++++ src/restic/testdata/expired_snapshots_3 | 497 +++++++++++++++++++++++ src/restic/testdata/expired_snapshots_4 | 497 +++++++++++++++++++++++ src/restic/testdata/expired_snapshots_5 | 17 + src/restic/testdata/expired_snapshots_6 | 52 +++ src/restic/testdata/expired_snapshots_7 | 152 +++++++ src/restic/testdata/expired_snapshots_8 | 52 +++ src/restic/testdata/expired_snapshots_9 | 62 +++ src/restic/testdata/filter_snapshots_0 | 162 ++++++++ src/restic/testdata/filter_snapshots_1 | 32 ++ src/restic/testdata/filter_snapshots_2 | 22 + src/restic/testdata/filter_snapshots_3 | 162 ++++++++ src/restic/testdata/filter_snapshots_4 | 22 + src/restic/testdata/filter_snapshots_5 | 22 + 26 files changed, 3080 insertions(+), 1 deletion(-) create mode 100644 src/restic/snapshot_filter.go create mode 100644 src/restic/snapshot_filter_test.go create mode 100644 src/restic/testdata/expired_snapshots_0 create mode 100644 src/restic/testdata/expired_snapshots_1 create mode 100644 src/restic/testdata/expired_snapshots_10 create mode 100644 src/restic/testdata/expired_snapshots_11 create mode 100644 src/restic/testdata/expired_snapshots_12 create mode 100644 src/restic/testdata/expired_snapshots_13 create mode 100644 src/restic/testdata/expired_snapshots_14 create mode 100644 src/restic/testdata/expired_snapshots_15 create mode 100644 src/restic/testdata/expired_snapshots_16 create mode 100644 src/restic/testdata/expired_snapshots_2 create mode 100644 src/restic/testdata/expired_snapshots_3 create mode 100644 src/restic/testdata/expired_snapshots_4 create mode 100644 src/restic/testdata/expired_snapshots_5 create mode 100644 src/restic/testdata/expired_snapshots_6 create mode 100644 src/restic/testdata/expired_snapshots_7 create mode 100644 src/restic/testdata/expired_snapshots_8 create mode 100644 src/restic/testdata/expired_snapshots_9 create mode 100644 src/restic/testdata/filter_snapshots_0 create mode 100644 src/restic/testdata/filter_snapshots_1 create mode 100644 src/restic/testdata/filter_snapshots_2 create mode 100644 src/restic/testdata/filter_snapshots_3 create mode 100644 src/restic/testdata/filter_snapshots_4 create mode 100644 src/restic/testdata/filter_snapshots_5 diff --git a/src/restic/snapshot.go b/src/restic/snapshot.go index 4a8339d44..3eaa0b61f 100644 --- a/src/restic/snapshot.go +++ b/src/restic/snapshot.go @@ -83,7 +83,8 @@ func LoadAllSnapshots(repo *repository.Repository) (snapshots []*Snapshot, err e } func (sn Snapshot) String() string { - return fmt.Sprintf("", sn.id.Str(), sn.Paths, sn.Time) + return fmt.Sprintf("", + sn.id.Str(), sn.Paths, sn.Time, sn.Username, sn.Hostname) } // ID retuns the snapshot's ID. diff --git a/src/restic/snapshot_filter.go b/src/restic/snapshot_filter.go new file mode 100644 index 000000000..589b4bd4e --- /dev/null +++ b/src/restic/snapshot_filter.go @@ -0,0 +1,195 @@ +package restic + +import ( + "fmt" + "reflect" + "sort" + "time" +) + +// Snapshots is a list of snapshots. +type Snapshots []*Snapshot + +// Len returns the number of snapshots in sn. +func (sn Snapshots) Len() int { + return len(sn) +} + +// Less returns true iff the ith snapshot has been made after the jth. +func (sn Snapshots) Less(i, j int) bool { + return sn[i].Time.After(sn[j].Time) +} + +// Swap exchanges the two snapshots. +func (sn Snapshots) Swap(i, j int) { + sn[i], sn[j] = sn[j], sn[i] +} + +// SnapshotFilter configures criteria for filtering snapshots before an +// ExpirePolicy can be applied. +type SnapshotFilter struct { + Hostname string + Username string + Paths []string +} + +// FilterSnapshots returns the snapshots from s which match the filter f. +func FilterSnapshots(s Snapshots, f SnapshotFilter) (result Snapshots) { + for _, snap := range s { + if f.Hostname != "" && f.Hostname != snap.Hostname { + continue + } + + if f.Username != "" && f.Username != snap.Username { + continue + } + + if f.Paths != nil && !reflect.DeepEqual(f.Paths, snap.Paths) { + continue + } + + result = append(result, snap) + } + + return result +} + +// ExpirePolicy configures which snapshots should be automatically removed. +type ExpirePolicy struct { + Last int // keep the last n snapshots + Daily int // keep the last n daily snapshots + Weekly int // keep the last n weekly snapshots + Monthly int // keep the last n monthly snapshots + Yearly int // keep the last n yearly snapshots +} + +// Sum returns the maximum number of snapshots to be kept according to this +// policy. +func (e ExpirePolicy) Sum() int { + return e.Last + e.Daily + e.Weekly + e.Monthly + e.Yearly +} + +// filter is used to split a list of snapshots into those to keep and those to +// remove according to a policy. +type filter struct { + Unprocessed Snapshots + Remove Snapshots + Keep Snapshots +} + +func (f filter) String() string { + return fmt.Sprintf("", len(f.Unprocessed), len(f.Keep), len(f.Remove)) +} + +// ymd returns an integer in the form YYYYMMDD. +func ymd(d time.Time) int { + return d.Year()*10000 + int(d.Month())*100 + d.Day() +} + +// yw returns an integer in the form YYYYWW, where WW is the week number. +func yw(d time.Time) int { + year, week := d.ISOWeek() + return year*100 + week +} + +// ym returns an integer in the form YYYYMM. +func ym(d time.Time) int { + return d.Year()*100 + int(d.Month()) +} + +// y returns the year of d. +func y(d time.Time) int { + return d.Year() +} + +// apply moves snapshots from Unprocess to either Keep or Remove. It sorts the +// snapshots into buckets according to the return of fn, and then moves the +// newest snapshot in each bucket to Keep and all others to Remove. When max +// snapshots were found, processing stops. +func (f *filter) apply(fn func(time.Time) int, max int) { + if max == 0 || len(f.Unprocessed) == 0 { + return + } + + sameDay := Snapshots{} + lastDay := fn(f.Unprocessed[0].Time) + + for len(f.Unprocessed) > 0 { + cur := f.Unprocessed[0] + + day := fn(cur.Time) + + // if the snapshots are from a new day, forget all but the first (=last + // in time) snapshot from the previous day. + if day != lastDay { + f.Keep = append(f.Keep, sameDay[0]) + for _, snapshot := range sameDay[1:] { + f.Remove = append(f.Remove, snapshot) + } + + sameDay = Snapshots{} + lastDay = day + max-- + + if max == 0 { + break + } + } + + // collect all snapshots for the current day + sameDay = append(sameDay, cur) + f.Unprocessed = f.Unprocessed[1:] + } + + if len(sameDay) > 0 { + f.Keep = append(f.Keep, sameDay[0]) + for _, snapshot := range sameDay[1:] { + f.Remove = append(f.Remove, snapshot) + } + } +} + +// keepLast marks the last n snapshots as to be kept. +func (f *filter) keepLast(n int) { + if n > len(f.Unprocessed) { + n = len(f.Unprocessed) + } + + f.Keep = append(f.Keep, f.Unprocessed[:n]...) + f.Unprocessed = f.Unprocessed[n:] +} + +// finish moves all remaining snapshots to remove. +func (f *filter) finish() { + f.Remove = append(f.Remove, f.Unprocessed...) +} + +// ApplyPolicy runs returns the snapshots from s that are to be deleted according +// to the policy p. s is sorted in the process. +func ApplyPolicy(list Snapshots, p ExpirePolicy) (keep, remove Snapshots) { + sort.Sort(list) + + empty := ExpirePolicy{} + if p == empty { + return list, remove + } + + if len(list) == 0 { + return list, remove + } + + f := filter{ + Unprocessed: list, + Remove: Snapshots{}, + Keep: Snapshots{}, + } + + f.keepLast(p.Last) + f.apply(ymd, p.Daily) + f.apply(yw, p.Weekly) + f.apply(ym, p.Monthly) + f.apply(y, p.Yearly) + f.finish() + + return f.Keep, f.Remove +} diff --git a/src/restic/snapshot_filter_test.go b/src/restic/snapshot_filter_test.go new file mode 100644 index 000000000..6bf65b9be --- /dev/null +++ b/src/restic/snapshot_filter_test.go @@ -0,0 +1,262 @@ +package restic + +import ( + "encoding/json" + "fmt" + "io/ioutil" + "path/filepath" + "reflect" + "sort" + "testing" + "time" +) + +func parseTime(s string) time.Time { + t, err := time.Parse("2006-01-02 15:04:05 -0700", s) + if err != nil { + panic(err) + } + + return t.Local() +} + +var testFilterSnapshots = Snapshots{ + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-01 01:02:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "bar", Username: "testuser", Time: parseTime("2016-01-01 01:03:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-03 07:02:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "bar", Username: "testuser", Time: parseTime("2016-01-01 07:08:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-04 10:23:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-04 11:23:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-04 12:23:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-04 12:24:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-04 12:28:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-04 12:30:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-04 16:23:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-05 09:02:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-06 08:02:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-07 10:02:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "root", Time: parseTime("2016-01-08 20:02:03 +0100"), Paths: []string{"/usr", "/sbin"}}, + {Hostname: "foo", Username: "root", Time: parseTime("2016-01-09 21:02:03 +0100"), Paths: []string{"/usr", "/sbin"}}, + {Hostname: "bar", Username: "root", Time: parseTime("2016-01-12 21:02:03 +0100"), Paths: []string{"/usr", "/sbin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-12 21:08:03 +0100"), Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "testuser", Time: parseTime("2016-01-18 12:02:03 +0100"), Paths: []string{"/usr", "/bin"}}, +} + +var filterTests = []SnapshotFilter{ + {Hostname: "foo"}, + {Username: "root"}, + {Hostname: "foo", Username: "root"}, + {Paths: []string{"/usr", "/bin"}}, + {Hostname: "bar", Paths: []string{"/usr", "/bin"}}, + {Hostname: "foo", Username: "root", Paths: []string{"/usr", "/sbin"}}, +} + +func TestFilterSnapshots(t *testing.T) { + sort.Sort(testFilterSnapshots) + + for i, f := range filterTests { + res := FilterSnapshots(testFilterSnapshots, f) + + goldenFilename := filepath.Join("testdata", fmt.Sprintf("filter_snapshots_%d", i)) + + if *updateGoldenFiles { + buf, err := json.MarshalIndent(res, "", " ") + 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 err != nil { + t.Errorf("error loading golden file %v: %v", goldenFilename, err) + continue + } + + var want Snapshots + err = json.Unmarshal(buf, &want) + + if !reflect.DeepEqual(res, want) { + t.Errorf("test %v: wrong result, want:\n %#v\ngot:\n %#v", i, want, res) + continue + } + } +} + +var testExpireSnapshots = Snapshots{ + {Time: parseTime("2014-09-01 10:20:30 +0100")}, + {Time: parseTime("2014-09-02 10:20:30 +0100")}, + {Time: parseTime("2014-09-05 10:20:30 +0100")}, + {Time: parseTime("2014-09-06 10:20:30 +0100")}, + {Time: parseTime("2014-09-08 10:20:30 +0100")}, + {Time: parseTime("2014-09-09 10:20:30 +0100")}, + {Time: parseTime("2014-09-10 10:20:30 +0100")}, + {Time: parseTime("2014-09-11 10:20:30 +0100")}, + {Time: parseTime("2014-09-20 10:20:30 +0100")}, + {Time: parseTime("2014-09-22 10:20:30 +0100")}, + {Time: parseTime("2014-08-08 10:20:30 +0100")}, + {Time: parseTime("2014-08-10 10:20:30 +0100")}, + {Time: parseTime("2014-08-12 10:20:30 +0100")}, + {Time: parseTime("2014-08-13 10:20:30 +0100")}, + {Time: parseTime("2014-08-13 10:20:30 +0100")}, + {Time: parseTime("2014-08-15 10:20:30 +0100")}, + {Time: parseTime("2014-08-18 10:20:30 +0100")}, + {Time: parseTime("2014-08-20 10:20:30 +0100")}, + {Time: parseTime("2014-08-21 10:20:30 +0100")}, + {Time: parseTime("2014-08-22 10:20:30 +0100")}, + {Time: parseTime("2014-10-01 10:20:30 +0100")}, + {Time: parseTime("2014-10-02 10:20:30 +0100")}, + {Time: parseTime("2014-10-05 10:20:30 +0100")}, + {Time: parseTime("2014-10-06 10:20:30 +0100")}, + {Time: parseTime("2014-10-08 10:20:30 +0100")}, + {Time: parseTime("2014-10-09 10:20:30 +0100")}, + {Time: parseTime("2014-10-10 10:20:30 +0100")}, + {Time: parseTime("2014-10-11 10:20:30 +0100")}, + {Time: parseTime("2014-10-20 10:20:30 +0100")}, + {Time: parseTime("2014-10-22 10:20:30 +0100")}, + {Time: parseTime("2014-11-08 10:20:30 +0100")}, + {Time: parseTime("2014-11-10 10:20:30 +0100")}, + {Time: parseTime("2014-11-12 10:20:30 +0100")}, + {Time: parseTime("2014-11-13 10:20:30 +0100")}, + {Time: parseTime("2014-11-13 10:20:30 +0100")}, + {Time: parseTime("2014-11-15 10:20:30 +0100")}, + {Time: parseTime("2014-11-18 10:20:30 +0100")}, + {Time: parseTime("2014-11-20 10:20:30 +0100")}, + {Time: parseTime("2014-11-21 10:20:30 +0100")}, + {Time: parseTime("2014-11-22 10:20:30 +0100")}, + {Time: parseTime("2015-09-01 10:20:30 +0100")}, + {Time: parseTime("2015-09-02 10:20:30 +0100")}, + {Time: parseTime("2015-09-05 10:20:30 +0100")}, + {Time: parseTime("2015-09-06 10:20:30 +0100")}, + {Time: parseTime("2015-09-08 10:20:30 +0100")}, + {Time: parseTime("2015-09-09 10:20:30 +0100")}, + {Time: parseTime("2015-09-10 10:20:30 +0100")}, + {Time: parseTime("2015-09-11 10:20:30 +0100")}, + {Time: parseTime("2015-09-20 10:20:30 +0100")}, + {Time: parseTime("2015-09-22 10:20:30 +0100")}, + {Time: parseTime("2015-08-08 10:20:30 +0100")}, + {Time: parseTime("2015-08-10 10:20:30 +0100")}, + {Time: parseTime("2015-08-12 10:20:30 +0100")}, + {Time: parseTime("2015-08-13 10:20:30 +0100")}, + {Time: parseTime("2015-08-13 10:20:30 +0100")}, + {Time: parseTime("2015-08-15 10:20:30 +0100")}, + {Time: parseTime("2015-08-18 10:20:30 +0100")}, + {Time: parseTime("2015-08-20 10:20:30 +0100")}, + {Time: parseTime("2015-08-21 10:20:30 +0100")}, + {Time: parseTime("2015-08-22 10:20:30 +0100")}, + {Time: parseTime("2015-10-01 10:20:30 +0100")}, + {Time: parseTime("2015-10-02 10:20:30 +0100")}, + {Time: parseTime("2015-10-05 10:20:30 +0100")}, + {Time: parseTime("2015-10-06 10:20:30 +0100")}, + {Time: parseTime("2015-10-08 10:20:30 +0100")}, + {Time: parseTime("2015-10-09 10:20:30 +0100")}, + {Time: parseTime("2015-10-10 10:20:30 +0100")}, + {Time: parseTime("2015-10-11 10:20:30 +0100")}, + {Time: parseTime("2015-10-20 10:20:30 +0100")}, + {Time: parseTime("2015-10-22 10:20:30 +0100")}, + {Time: parseTime("2015-11-08 10:20:30 +0100")}, + {Time: parseTime("2015-11-10 10:20:30 +0100")}, + {Time: parseTime("2015-11-12 10:20:30 +0100")}, + {Time: parseTime("2015-11-13 10:20:30 +0100")}, + {Time: parseTime("2015-11-13 10:20:30 +0100")}, + {Time: parseTime("2015-11-15 10:20:30 +0100")}, + {Time: parseTime("2015-11-18 10:20:30 +0100")}, + {Time: parseTime("2015-11-20 10:20:30 +0100")}, + {Time: parseTime("2015-11-21 10:20:30 +0100")}, + {Time: parseTime("2015-11-22 10:20:30 +0100")}, + {Time: parseTime("2016-01-01 01:02:03 +0100")}, + {Time: parseTime("2016-01-01 01:03:03 +0100")}, + {Time: parseTime("2016-01-01 07:08:03 +0100")}, + {Time: parseTime("2016-01-03 07:02:03 +0100")}, + {Time: parseTime("2016-01-04 10:23:03 +0100")}, + {Time: parseTime("2016-01-04 11:23:03 +0100")}, + {Time: parseTime("2016-01-04 12:23:03 +0100")}, + {Time: parseTime("2016-01-04 12:24:03 +0100")}, + {Time: parseTime("2016-01-04 12:28:03 +0100")}, + {Time: parseTime("2016-01-04 12:30:03 +0100")}, + {Time: parseTime("2016-01-04 16:23:03 +0100")}, + {Time: parseTime("2016-01-05 09:02:03 +0100")}, + {Time: parseTime("2016-01-06 08:02:03 +0100")}, + {Time: parseTime("2016-01-07 10:02:03 +0100")}, + {Time: parseTime("2016-01-08 20:02:03 +0100")}, + {Time: parseTime("2016-01-09 21:02:03 +0100")}, + {Time: parseTime("2016-01-12 21:02:03 +0100")}, + {Time: parseTime("2016-01-12 21:08:03 +0100")}, + {Time: parseTime("2016-01-18 12:02:03 +0100")}, +} + +var expireTests = []ExpirePolicy{ + {}, + {Last: 10}, + {Last: 15}, + {Last: 99}, + {Last: 200}, + {Daily: 3}, + {Daily: 10}, + {Daily: 30}, + {Last: 5, Daily: 5}, + {Last: 2, Daily: 10}, + {Weekly: 2}, + {Weekly: 4}, + {Daily: 3, Weekly: 4}, + {Monthly: 6}, + {Daily: 2, Weekly: 2, Monthly: 6}, + {Yearly: 10}, + {Daily: 7, Weekly: 2, Monthly: 3, Yearly: 10}, +} + +func TestApplyPolicy(t *testing.T) { + for i, p := range expireTests { + keep, remove := 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) + + 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)) + } + + for _, sn := range keep { + t.Logf("test %d: keep snapshot at %v\n", i, sn.Time) + } + for _, sn := range remove { + t.Logf("test %d: forget snapshot at %v\n", i, sn.Time) + } + + goldenFilename := filepath.Join("testdata", fmt.Sprintf("expired_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 err != nil { + t.Errorf("error loading golden file %v: %v", goldenFilename, err) + continue + } + + var want 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/expired_snapshots_0 b/src/restic/testdata/expired_snapshots_0 new file mode 100644 index 000000000..d83ec624e --- /dev/null +++ b/src/restic/testdata/expired_snapshots_0 @@ -0,0 +1,497 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:30:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:28:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:24:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T11:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T10:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T07:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T01:03:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T01:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-21T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-20T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-18T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-15T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-12T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-10T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-08T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-21T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-18T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-15T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-12T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-21T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-20T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-18T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-15T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-12T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-10T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-08T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-21T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-18T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-15T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-12T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-08T11:20:30+02:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_1 b/src/restic/testdata/expired_snapshots_1 new file mode 100644 index 000000000..5a6f3e8af --- /dev/null +++ b/src/restic/testdata/expired_snapshots_1 @@ -0,0 +1,52 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:30:03+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_10 b/src/restic/testdata/expired_snapshots_10 new file mode 100644 index 000000000..853fdce73 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_10 @@ -0,0 +1,12 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_11 b/src/restic/testdata/expired_snapshots_11 new file mode 100644 index 000000000..c89b120a9 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_11 @@ -0,0 +1,22 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_12 b/src/restic/testdata/expired_snapshots_12 new file mode 100644 index 000000000..240906b19 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_12 @@ -0,0 +1,37 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-15T10:20:30+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_13 b/src/restic/testdata/expired_snapshots_13 new file mode 100644 index 000000000..938a85271 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_13 @@ -0,0 +1,32 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-22T10:20:30+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_14 b/src/restic/testdata/expired_snapshots_14 new file mode 100644 index 000000000..52f6b1aa1 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_14 @@ -0,0 +1,52 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-22T11:20:30+02:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_15 b/src/restic/testdata/expired_snapshots_15 new file mode 100644 index 000000000..aaf743f09 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_15 @@ -0,0 +1,17 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-22T10:20:30+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_16 b/src/restic/testdata/expired_snapshots_16 new file mode 100644 index 000000000..eddb2c833 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_16 @@ -0,0 +1,72 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-22T10:20:30+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_2 b/src/restic/testdata/expired_snapshots_2 new file mode 100644 index 000000000..fcc8bb973 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_2 @@ -0,0 +1,77 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:30:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:28:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:24:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T11:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T10:23:03+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_3 b/src/restic/testdata/expired_snapshots_3 new file mode 100644 index 000000000..d83ec624e --- /dev/null +++ b/src/restic/testdata/expired_snapshots_3 @@ -0,0 +1,497 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:30:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:28:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:24:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T11:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T10:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T07:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T01:03:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T01:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-21T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-20T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-18T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-15T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-12T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-10T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-08T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-21T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-18T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-15T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-12T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-21T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-20T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-18T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-15T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-12T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-10T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-08T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-21T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-18T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-15T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-12T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-08T11:20:30+02:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_4 b/src/restic/testdata/expired_snapshots_4 new file mode 100644 index 000000000..d83ec624e --- /dev/null +++ b/src/restic/testdata/expired_snapshots_4 @@ -0,0 +1,497 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:30:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:28:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:24:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T12:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T11:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T10:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T07:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T01:03:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T01:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-21T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-20T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-18T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-15T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-12T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-10T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-08T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-21T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-18T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-15T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-12T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-08-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-21T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-20T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-18T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-15T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-12T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-10T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-11-08T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-10-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-09-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-21T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-18T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-15T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-13T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-12T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2014-08-08T11:20:30+02:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_5 b/src/restic/testdata/expired_snapshots_5 new file mode 100644 index 000000000..e862779c0 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_5 @@ -0,0 +1,17 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_6 b/src/restic/testdata/expired_snapshots_6 new file mode 100644 index 000000000..6f53af139 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_6 @@ -0,0 +1,52 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T07:08:03+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_7 b/src/restic/testdata/expired_snapshots_7 new file mode 100644 index 000000000..750da193f --- /dev/null +++ b/src/restic/testdata/expired_snapshots_7 @@ -0,0 +1,152 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T07:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-22T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-21T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-20T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-18T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-15T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-13T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-12T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-10T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-08T10:20:30+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-22T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-20T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-11T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-10T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-09T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-08T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-06T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-05T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-02T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-10-01T11:20:30+02:00", + "tree": null, + "paths": null + }, + { + "time": "2015-09-22T11:20:30+02:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_8 b/src/restic/testdata/expired_snapshots_8 new file mode 100644 index 000000000..fd72ec6a5 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_8 @@ -0,0 +1,52 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/expired_snapshots_9 b/src/restic/testdata/expired_snapshots_9 new file mode 100644 index 000000000..63fbd8b09 --- /dev/null +++ b/src/restic/testdata/expired_snapshots_9 @@ -0,0 +1,62 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-12T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2016-01-01T07:08:03+01:00", + "tree": null, + "paths": null + }, + { + "time": "2015-11-22T10:20:30+01:00", + "tree": null, + "paths": null + } +] \ No newline at end of file diff --git a/src/restic/testdata/filter_snapshots_0 b/src/restic/testdata/filter_snapshots_0 new file mode 100644 index 000000000..022aa7aec --- /dev/null +++ b/src/restic/testdata/filter_snapshots_0 @@ -0,0 +1,162 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/sbin" + ], + "hostname": "foo", + "username": "root" + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/sbin" + ], + "hostname": "foo", + "username": "root" + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T12:30:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T12:28:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T12:24:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T12:23:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T11:23:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T10:23:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-01T01:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + } +] \ No newline at end of file diff --git a/src/restic/testdata/filter_snapshots_1 b/src/restic/testdata/filter_snapshots_1 new file mode 100644 index 000000000..1239b4813 --- /dev/null +++ b/src/restic/testdata/filter_snapshots_1 @@ -0,0 +1,32 @@ +[ + { + "time": "2016-01-12T21:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/sbin" + ], + "hostname": "bar", + "username": "root" + }, + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/sbin" + ], + "hostname": "foo", + "username": "root" + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/sbin" + ], + "hostname": "foo", + "username": "root" + } +] \ No newline at end of file diff --git a/src/restic/testdata/filter_snapshots_2 b/src/restic/testdata/filter_snapshots_2 new file mode 100644 index 000000000..1bde9e513 --- /dev/null +++ b/src/restic/testdata/filter_snapshots_2 @@ -0,0 +1,22 @@ +[ + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/sbin" + ], + "hostname": "foo", + "username": "root" + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/sbin" + ], + "hostname": "foo", + "username": "root" + } +] \ No newline at end of file diff --git a/src/restic/testdata/filter_snapshots_3 b/src/restic/testdata/filter_snapshots_3 new file mode 100644 index 000000000..bf120b32b --- /dev/null +++ b/src/restic/testdata/filter_snapshots_3 @@ -0,0 +1,162 @@ +[ + { + "time": "2016-01-18T12:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-12T21:08:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-07T10:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-06T08:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-05T09:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T16:23:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T12:30:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T12:28:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T12:24:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T12:23:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T11:23:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-04T10:23:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-03T07:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + }, + { + "time": "2016-01-01T07:08:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "bar", + "username": "testuser" + }, + { + "time": "2016-01-01T01:03:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "bar", + "username": "testuser" + }, + { + "time": "2016-01-01T01:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "foo", + "username": "testuser" + } +] \ No newline at end of file diff --git a/src/restic/testdata/filter_snapshots_4 b/src/restic/testdata/filter_snapshots_4 new file mode 100644 index 000000000..2c566811f --- /dev/null +++ b/src/restic/testdata/filter_snapshots_4 @@ -0,0 +1,22 @@ +[ + { + "time": "2016-01-01T07:08:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "bar", + "username": "testuser" + }, + { + "time": "2016-01-01T01:03:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/bin" + ], + "hostname": "bar", + "username": "testuser" + } +] \ No newline at end of file diff --git a/src/restic/testdata/filter_snapshots_5 b/src/restic/testdata/filter_snapshots_5 new file mode 100644 index 000000000..1bde9e513 --- /dev/null +++ b/src/restic/testdata/filter_snapshots_5 @@ -0,0 +1,22 @@ +[ + { + "time": "2016-01-09T21:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/sbin" + ], + "hostname": "foo", + "username": "root" + }, + { + "time": "2016-01-08T20:02:03+01:00", + "tree": null, + "paths": [ + "/usr", + "/sbin" + ], + "hostname": "foo", + "username": "root" + } +] \ No newline at end of file