mirror of
https://github.com/restic/restic.git
synced 2024-12-23 00:07:25 +00:00
fuse: Better check for whether snapshots changed
We previously checked whether the set of snapshots might have changed based only on their number, which fails when as many snapshots are forgotten as are added. Check for the SHA-256 of their id's instead.
This commit is contained in:
parent
59a90943bb
commit
c091e43b33
1 changed files with 24 additions and 6 deletions
|
@ -4,6 +4,7 @@
|
||||||
package fuse
|
package fuse
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"bytes"
|
||||||
"context"
|
"context"
|
||||||
"fmt"
|
"fmt"
|
||||||
"path"
|
"path"
|
||||||
|
@ -14,6 +15,8 @@ import (
|
||||||
|
|
||||||
"github.com/restic/restic/internal/debug"
|
"github.com/restic/restic/internal/debug"
|
||||||
"github.com/restic/restic/internal/restic"
|
"github.com/restic/restic/internal/restic"
|
||||||
|
|
||||||
|
"github.com/minio/sha256-simd"
|
||||||
)
|
)
|
||||||
|
|
||||||
type MetaDirData struct {
|
type MetaDirData struct {
|
||||||
|
@ -39,7 +42,7 @@ type SnapshotsDirStructure struct {
|
||||||
// that way we don't need path processing special cases when using the entries tree
|
// that way we don't need path processing special cases when using the entries tree
|
||||||
entries map[string]*MetaDirData
|
entries map[string]*MetaDirData
|
||||||
|
|
||||||
snCount int
|
hash [sha256.Size]byte // Hash at last check.
|
||||||
lastCheck time.Time
|
lastCheck time.Time
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -49,7 +52,6 @@ func NewSnapshotsDirStructure(root *Root, pathTemplates []string, timeTemplate s
|
||||||
root: root,
|
root: root,
|
||||||
pathTemplates: pathTemplates,
|
pathTemplates: pathTemplates,
|
||||||
timeTemplate: timeTemplate,
|
timeTemplate: timeTemplate,
|
||||||
snCount: -1,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -302,10 +304,26 @@ func (d *SnapshotsDirStructure) updateSnapshots(ctx context.Context) error {
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
// sort snapshots ascending by time (default order is descending)
|
|
||||||
sort.Sort(sort.Reverse(snapshots))
|
|
||||||
|
|
||||||
if d.snCount == len(snapshots) {
|
// Sort snapshots ascending by time, using the id to break ties.
|
||||||
|
// This needs to be done before hashing.
|
||||||
|
sort.Slice(snapshots, func(i, j int) bool {
|
||||||
|
si, sj := snapshots[i], snapshots[j]
|
||||||
|
if si.Time.Equal(sj.Time) {
|
||||||
|
return bytes.Compare(si.ID()[:], sj.ID()[:]) < 0
|
||||||
|
}
|
||||||
|
return si.Time.Before(sj.Time)
|
||||||
|
})
|
||||||
|
|
||||||
|
// We update the snapshots when the hash of their id's changes.
|
||||||
|
h := sha256.New()
|
||||||
|
for _, sn := range snapshots {
|
||||||
|
h.Write(sn.ID()[:])
|
||||||
|
}
|
||||||
|
var hash [sha256.Size]byte
|
||||||
|
h.Sum(hash[:0])
|
||||||
|
|
||||||
|
if d.hash == hash {
|
||||||
d.lastCheck = time.Now()
|
d.lastCheck = time.Now()
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
@ -316,7 +334,7 @@ func (d *SnapshotsDirStructure) updateSnapshots(ctx context.Context) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
d.lastCheck = time.Now()
|
d.lastCheck = time.Now()
|
||||||
d.snCount = len(snapshots)
|
d.hash = hash
|
||||||
d.makeDirs(snapshots)
|
d.makeDirs(snapshots)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue