From f05405fe1ce4c78a8c75e27920c863c5b83686bd Mon Sep 17 00:00:00 2001 From: Mark McDowall Date: Mon, 22 May 2023 22:10:43 -0700 Subject: [PATCH] Fixed: Don't rollback file move if destination already exists Towards #5610 --- .../DiskTests/DiskTransferServiceFixture.cs | 20 +++++++++++++++++++ .../Disk/DiskTransferService.cs | 8 ++++++-- 2 files changed, 26 insertions(+), 2 deletions(-) diff --git a/src/NzbDrone.Common.Test/DiskTests/DiskTransferServiceFixture.cs b/src/NzbDrone.Common.Test/DiskTests/DiskTransferServiceFixture.cs index 93607c665..cd491e68a 100644 --- a/src/NzbDrone.Common.Test/DiskTests/DiskTransferServiceFixture.cs +++ b/src/NzbDrone.Common.Test/DiskTests/DiskTransferServiceFixture.cs @@ -351,6 +351,26 @@ namespace NzbDrone.Common.Test.DiskTests .Verify(v => v.DeleteFile(_targetPath), Times.Once()); } + [Test] + public void should_not_rollback_move_on_partial_if_destination_already_exists() + { + Mocker.GetMock() + .Setup(v => v.MoveFile(_sourcePath, _targetPath, false)) + .Callback(() => + { + WithExistingFile(_targetPath, true, 900); + }); + + Mocker.GetMock() + .Setup(v => v.MoveFile(_sourcePath, _targetPath, false)) + .Throws(new FileAlreadyExistsException("File already exists", _targetPath)); + + Assert.Throws(() => Subject.TransferFile(_sourcePath, _targetPath, TransferMode.Move)); + + Mocker.GetMock() + .Verify(v => v.DeleteFile(_targetPath), Times.Never()); + } + [Test] public void should_log_error_if_rollback_partialmove_fails() { diff --git a/src/NzbDrone.Common/Disk/DiskTransferService.cs b/src/NzbDrone.Common/Disk/DiskTransferService.cs index 83d815348..fb7d93f48 100644 --- a/src/NzbDrone.Common/Disk/DiskTransferService.cs +++ b/src/NzbDrone.Common/Disk/DiskTransferService.cs @@ -500,9 +500,13 @@ namespace NzbDrone.Common.Disk throw new IOException(string.Format("File move incomplete, data loss may have occurred. [{0}] was {1} bytes long instead of the expected {2}.", targetPath, targetSize, originalSize)); } } - catch + catch (Exception ex) { - RollbackPartialMove(sourcePath, targetPath); + if (ex is not FileAlreadyExistsException) + { + RollbackPartialMove(sourcePath, targetPath); + } + throw; } }