mirror of https://github.com/restic/restic.git
restore: fix corrupted sparse files
This commit is contained in:
parent
1eccd6504b
commit
f1c76a8286
|
@ -153,6 +153,12 @@ func (r *fileRestorer) restoreFiles(ctx context.Context) error {
|
||||||
// in addition, a short chunk will never match r.zeroChunk which would prevent sparseness for short files
|
// in addition, a short chunk will never match r.zeroChunk which would prevent sparseness for short files
|
||||||
file.sparse = r.sparse
|
file.sparse = r.sparse
|
||||||
}
|
}
|
||||||
|
if file.state != nil {
|
||||||
|
// The restorer currently cannot punch new holes into an existing files.
|
||||||
|
// Thus sections that contained data but should be sparse after restoring
|
||||||
|
// the snapshot would still contain the old data resulting in a corrupt restore.
|
||||||
|
file.sparse = false
|
||||||
|
}
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
// repository index is messed up, can't do anything
|
// repository index is messed up, can't do anything
|
||||||
|
|
|
@ -895,6 +895,44 @@ func TestRestorerSparseFiles(t *testing.T) {
|
||||||
len(zeros), blocks, 100*sparsity)
|
len(zeros), blocks, 100*sparsity)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestRestorerSparseOverwrite(t *testing.T) {
|
||||||
|
baseSnapshot := Snapshot{
|
||||||
|
Nodes: map[string]Node{
|
||||||
|
"foo": File{Data: "content: new\n"},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
var zero [14]byte
|
||||||
|
sparseSnapshot := Snapshot{
|
||||||
|
Nodes: map[string]Node{
|
||||||
|
"foo": File{Data: string(zero[:])},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
repo := repository.TestRepository(t)
|
||||||
|
tempdir := filepath.Join(rtest.TempDir(t), "target")
|
||||||
|
ctx, cancel := context.WithCancel(context.Background())
|
||||||
|
defer cancel()
|
||||||
|
|
||||||
|
// base snapshot
|
||||||
|
sn, id := saveSnapshot(t, repo, baseSnapshot, noopGetGenericAttributes)
|
||||||
|
t.Logf("base snapshot saved as %v", id.Str())
|
||||||
|
|
||||||
|
res := NewRestorer(repo, sn, Options{Sparse: true})
|
||||||
|
err := res.RestoreTo(ctx, tempdir)
|
||||||
|
rtest.OK(t, err)
|
||||||
|
|
||||||
|
// sparse snapshot
|
||||||
|
sn, id = saveSnapshot(t, repo, sparseSnapshot, noopGetGenericAttributes)
|
||||||
|
t.Logf("base snapshot saved as %v", id.Str())
|
||||||
|
|
||||||
|
res = NewRestorer(repo, sn, Options{Sparse: true, Overwrite: OverwriteAlways})
|
||||||
|
err = res.RestoreTo(ctx, tempdir)
|
||||||
|
rtest.OK(t, err)
|
||||||
|
files, err := res.VerifyFiles(ctx, tempdir)
|
||||||
|
rtest.OK(t, err)
|
||||||
|
rtest.Equals(t, 1, files, "unexpected number of verified files")
|
||||||
|
}
|
||||||
|
|
||||||
func TestRestorerOverwriteBehavior(t *testing.T) {
|
func TestRestorerOverwriteBehavior(t *testing.T) {
|
||||||
baseTime := time.Now()
|
baseTime := time.Now()
|
||||||
baseSnapshot := Snapshot{
|
baseSnapshot := Snapshot{
|
||||||
|
|
Loading…
Reference in New Issue