From a6839ffda8b70f1d0697b5ead836cf6fba2e9ac0 Mon Sep 17 00:00:00 2001 From: abraunegg Date: Tue, 24 Jun 2025 18:10:15 +1000 Subject: [PATCH] Fix Bug #3344: Fix that a failed file download can lead to online deletion (#3351) * When a file fails to download, perform an additional test to ensure that the failed download does not exist on the local path, and if this does not exist, ensure that that identifiers used to download the file do not exist in the database. --- src/sync.d | 20 ++++++++++++++++++-- 1 file changed, 18 insertions(+), 2 deletions(-) diff --git a/src/sync.d b/src/sync.d index 291c6d76..9dff0195 100644 --- a/src/sync.d +++ b/src/sync.d @@ -3693,6 +3693,7 @@ class SyncEngine { } // If we get to this point, something was downloaded .. does it match what we expected? + // Does it still exist? if (exists(newItemPath)) { // When downloading some files from SharePoint, the OneDrive API reports one file size, // but the SharePoint HTTP Server sends a totally different byte count for the same file @@ -3769,7 +3770,7 @@ class SyncEngine { addLogEntry("ERROR: File download size mismatch. Increase logging verbosity to determine why."); } - // Hash Error + // Hash Error? if (downloadedFileHash != onlineFileHash) { // downloaded file hash does not match downloadValueMismatch = true; @@ -3866,6 +3867,7 @@ class SyncEngine { } } // end of (!disableDownloadValidation) } else { + // File does not exist locally addLogEntry("ERROR: File failed to download. Increase logging verbosity to determine why."); // Was this item previously in-sync with the local system? // We previously searched for the file in the DB, we need to use that record @@ -3911,12 +3913,26 @@ class SyncEngine { writeXattrData(newItemPath, onedriveJSONItem); } } else { - // Output download failed + // Output to the user that the file download failed addLogEntry("Downloading file: " ~ newItemPath ~ " ... failed!", ["info", "notify"]); + // Add the path to a list of items that failed to download if (!canFind(fileDownloadFailures, newItemPath)) { fileDownloadFailures ~= newItemPath; // Add newItemPath if it's not already present } + + // Since the file download failed: + // - The file should not exist locally + // - The download identifiers should not exist in the local database + if (!exists(newItemPath)) { + // The local path does not exist + if (itemDB.idInLocalDatabase(downloadDriveId, downloadItemId)) { + // Since the path does not exist, but the driveId and itemId exists in the database, when we do the DB consistency check, we will think this file has been 'deleted' + // The driveId and itemId online exists in our database - it needs to be removed so this does not occur + addLogEntry("Removing existing DB record due to failed file download."); + itemDB.deleteById(downloadDriveId, downloadItemId); + } + } } }