sync: don't allow syncs on overlapping remotes - fixes #2932
This commit is contained in:
parent
c5775cf73d
commit
84c650818e
4 changed files with 28 additions and 11 deletions
2
fs/fs.go
2
fs/fs.go
|
@ -61,7 +61,7 @@ var (
|
|||
ErrorNotAFile = errors.New("is a not a regular file")
|
||||
ErrorNotDeleting = errors.New("not deleting files as there were IO errors")
|
||||
ErrorNotDeletingDirs = errors.New("not deleting directories as there were IO errors")
|
||||
ErrorCantMoveOverlapping = errors.New("can't move files on overlapping remotes")
|
||||
ErrorOverlapping = errors.New("can't sync or move files on overlapping remotes")
|
||||
ErrorDirectoryNotEmpty = errors.New("directory not empty")
|
||||
ErrorImmutableModified = errors.New("immutable file modified")
|
||||
ErrorPermissionDenied = errors.New("permission denied")
|
||||
|
|
|
@ -532,7 +532,7 @@ func SameConfig(fdst, fsrc fs.Info) bool {
|
|||
|
||||
// Same returns true if fdst and fsrc point to the same underlying Fs
|
||||
func Same(fdst, fsrc fs.Info) bool {
|
||||
return SameConfig(fdst, fsrc) && fdst.Root() == fsrc.Root()
|
||||
return SameConfig(fdst, fsrc) && strings.Trim(fdst.Root(), "/") == strings.Trim(fsrc.Root(), "/")
|
||||
}
|
||||
|
||||
// Overlapping returns true if fdst and fsrc point to the same
|
||||
|
|
|
@ -64,6 +64,9 @@ type syncCopyMove struct {
|
|||
}
|
||||
|
||||
func newSyncCopyMove(fdst, fsrc fs.Fs, deleteMode fs.DeleteMode, DoMove bool, deleteEmptySrcDirs bool) (*syncCopyMove, error) {
|
||||
if (deleteMode != fs.DeleteModeOff || DoMove) && operations.Overlapping(fdst, fsrc) {
|
||||
return nil, fserrors.FatalError(fs.ErrorOverlapping)
|
||||
}
|
||||
s := &syncCopyMove{
|
||||
fdst: fdst,
|
||||
fsrc: fsrc,
|
||||
|
@ -920,13 +923,6 @@ func MoveDir(fdst, fsrc fs.Fs, deleteEmptySrcDirs bool) error {
|
|||
}
|
||||
}
|
||||
|
||||
// The two remotes mustn't overlap if we didn't do server side move
|
||||
if operations.Overlapping(fdst, fsrc) {
|
||||
err := fs.ErrorCantMoveOverlapping
|
||||
fs.Errorf(fdst, "%v", err)
|
||||
return err
|
||||
}
|
||||
|
||||
// Otherwise move the files one by one
|
||||
return moveDir(fdst, fsrc, deleteEmptySrcDirs)
|
||||
}
|
||||
|
|
|
@ -11,6 +11,7 @@ import (
|
|||
"github.com/ncw/rclone/fs"
|
||||
"github.com/ncw/rclone/fs/accounting"
|
||||
"github.com/ncw/rclone/fs/filter"
|
||||
"github.com/ncw/rclone/fs/fserrors"
|
||||
"github.com/ncw/rclone/fs/hash"
|
||||
"github.com/ncw/rclone/fs/operations"
|
||||
"github.com/ncw/rclone/fstest"
|
||||
|
@ -1102,7 +1103,7 @@ func TestServerSideMoveOverlap(t *testing.T) {
|
|||
|
||||
// Subdir move with no filters should return ErrorCantMoveOverlapping
|
||||
err = MoveDir(FremoteMove, r.Fremote, false)
|
||||
assert.EqualError(t, err, fs.ErrorCantMoveOverlapping.Error())
|
||||
assert.EqualError(t, err, fs.ErrorOverlapping.Error())
|
||||
|
||||
// Now try with a filter which should also fail with ErrorCantMoveOverlapping
|
||||
filter.Active.Opt.MinSize = 40
|
||||
|
@ -1110,7 +1111,27 @@ func TestServerSideMoveOverlap(t *testing.T) {
|
|||
filter.Active.Opt.MinSize = -1
|
||||
}()
|
||||
err = MoveDir(FremoteMove, r.Fremote, false)
|
||||
assert.EqualError(t, err, fs.ErrorCantMoveOverlapping.Error())
|
||||
assert.Equal(t, err, fs.ErrorOverlapping)
|
||||
}
|
||||
|
||||
// Test a sync with overlap
|
||||
func TestSyncOverlap(t *testing.T) {
|
||||
r := fstest.NewRun(t)
|
||||
defer r.Finalise()
|
||||
|
||||
subRemoteName := r.FremoteName + "/rclone-sync-test"
|
||||
FremoteSync, err := fs.NewFs(subRemoteName)
|
||||
require.NoError(t, err)
|
||||
|
||||
checkErr := func(err error) {
|
||||
assert.True(t, fserrors.IsFatalError(err))
|
||||
assert.Equal(t, err.Error(), fs.ErrorOverlapping.Error())
|
||||
}
|
||||
|
||||
checkErr(Sync(FremoteSync, r.Fremote))
|
||||
checkErr(Sync(r.Fremote, FremoteSync))
|
||||
checkErr(Sync(r.Fremote, r.Fremote))
|
||||
checkErr(Sync(FremoteSync, FremoteSync))
|
||||
}
|
||||
|
||||
// Test with BackupDir set
|
||||
|
|
Loading…
Reference in a new issue