diff --git a/docs/content/docs.md b/docs/content/docs.md index 19e157be0..09f7ae0e0 100644 --- a/docs/content/docs.md +++ b/docs/content/docs.md @@ -192,6 +192,8 @@ Checks the files in the source and destination match. It compares sizes and MD5SUMs and prints a report of files which don't match. It doesn't alter the source or destination. +`--size-only` may be used to only compare the sizes, not the MD5SUMs. + ### rclone dedupe remote:path ### By default `dedup` interactively finds duplicate files and offers to diff --git a/fs/operations.go b/fs/operations.go index f320047e8..d2eb6e223 100644 --- a/fs/operations.go +++ b/fs/operations.go @@ -684,6 +684,33 @@ func MoveDir(fdst, fsrc Fs) error { return nil } +// checkIdentical checks to see if dst and src are identical +// +// it returns true if differences were found +func checkIdentical(dst, src Object) bool { + Stats.Checking(src) + defer Stats.DoneChecking(src) + if src.Size() != dst.Size() { + Stats.Error() + ErrorLog(src, "Sizes differ") + return true + } + if !Config.SizeOnly { + same, _, err := CheckHashes(src, dst) + if err != nil { + // CheckHashes will log and count errors + return true + } + if !same { + Stats.Error() + ErrorLog(src, "Md5sums differ") + return true + } + } + Debug(src, "OK") + return false +} + // Check the files in fsrc and fdst according to Size and hash func Check(fdst, fsrc Fs) error { differences := int32(0) @@ -753,26 +780,9 @@ func Check(fdst, fsrc Fs) error { go func() { defer checkerWg.Done() for check := range checks { - dst, src := check[0], check[1] - Stats.Checking(src) - if src.Size() != dst.Size() { - Stats.DoneChecking(src) - Stats.Error() - ErrorLog(src, "Sizes differ") + if checkIdentical(check[0], check[1]) { atomic.AddInt32(&differences, 1) - continue } - same, _, err := CheckHashes(src, dst) - Stats.DoneChecking(src) - if err != nil { - continue - } - if !same { - Stats.Error() - atomic.AddInt32(&differences, 1) - ErrorLog(src, "Md5sums differ") - } - Debug(src, "OK") } }() } diff --git a/fs/operations_test.go b/fs/operations_test.go index 7b01d0830..6ddf92ec7 100644 --- a/fs/operations_test.go +++ b/fs/operations_test.go @@ -1003,8 +1003,13 @@ func TestCheck(t *testing.T) { fstest.CheckItems(t, r.fremote, file1, file3) check(3, 2) - r.WriteObject("potato2", "------------------------------------------------------------", t1) - fstest.CheckItems(t, r.fremote, file1, file2, file3) + file2r := file2 + if fs.Config.SizeOnly { + file2r = r.WriteObject("potato2", "--Some-Differences-But-Size-Only-Is-Enabled-----------------", t1) + } else { + r.WriteObject("potato2", "------------------------------------------------------------", t1) + } + fstest.CheckItems(t, r.fremote, file1, file2r, file3) check(4, 1) r.WriteFile("empty space", "", t2) @@ -1012,6 +1017,12 @@ func TestCheck(t *testing.T) { check(5, 0) } +func TestCheckSizeOnly(t *testing.T) { + fs.Config.SizeOnly = true + defer func() { fs.Config.SizeOnly = false }() + TestCheck(t) +} + func (r *Run) checkWithDuplicates(t *testing.T, items ...fstest.Item) { objects, size, err := fs.Count(r.fremote) if err != nil {