Resolve file / folder upload issues (Issue #598) (#602)

* Without this throw, uploadLastModifiedTime fails to catch that the 412 error was returned, thus, the retry with a null cTag / eTag is not performed which leads to 'OneDrive response missing required 'id' element' being generated.
* Fix 'Unexpected character '<'. (Line 1:1)' when OneDrive has an exception error
* Validate that the response from OneDrive is a valid JSON object
This commit is contained in:
abraunegg 2019-07-27 05:24:59 +10:00 committed by GitHub
parent f111eab71a
commit 3171318503
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 35 additions and 26 deletions

View file

@ -627,9 +627,8 @@ final class OneDriveApi
try {
json = content.parseJSON();
} catch (JSONException e) {
e.msg ~= "\n";
e.msg ~= content;
throw e;
// Log that a JSON Exception was caught, dont output the HTML response from OneDrive
log.vdebug("JSON Exception caught when performing HTTP operations - use --debug-https to diagnose further");
}
return json;
}
@ -780,7 +779,8 @@ final class OneDriveApi
// 412 - Precondition Failed
case 412:
log.vlog("OneDrive returned a 'HTTP 412 - Precondition Failed' - gracefully handling error");
break;
// Throw this as a specific exception so this is caught when performing uploadLastModifiedTime
throw new OneDriveException(http.statusLine.code, http.statusLine.reason, response);
// Server side (OneDrive) Errors
// 500 - Internal Server Error

View file

@ -1921,7 +1921,7 @@ final class SyncEngine
string parentPath = dirName(path); // will be either . or something else
try {
log.vdebug("Attempting to query OneDrive for this path: ", parentPath);
log.vdebug("Attempting to query OneDrive for this parent path: ", parentPath);
onedrivePathDetails = onedrive.getPathDetails(parentPath);
} catch (OneDriveException e) {
// exception - set onedriveParentRootDetails to a blank valid JSON
@ -2001,30 +2001,39 @@ final class SyncEngine
}
}
// https://docs.microsoft.com/en-us/windows/desktop/FileIO/naming-a-file
// Do not assume case sensitivity. For example, consider the names OSCAR, Oscar, and oscar to be the same,
// even though some file systems (such as a POSIX-compliant file system) may consider them as different.
// Note that NTFS supports POSIX semantics for case sensitivity but this is not the default behavior.
if (response["name"].str == baseName(path)){
// OneDrive 'name' matches local path name
log.vlog("The requested directory to create was found on OneDrive - skipping creating the directory: ", path );
// Check that this path is in the database
if (!itemdb.selectById(parent.driveId, parent.id, parent)){
// parent for 'path' is NOT in the database
log.vlog("The parent for this path is not in the local database - need to add parent to local database");
string parentPath = dirName(path);
uploadCreateDir(parentPath);
// response from OneDrive has to be a valid JSON object
if (response.type() == JSONType.object){
// https://docs.microsoft.com/en-us/windows/desktop/FileIO/naming-a-file
// Do not assume case sensitivity. For example, consider the names OSCAR, Oscar, and oscar to be the same,
// even though some file systems (such as a POSIX-compliant file system) may consider them as different.
// Note that NTFS supports POSIX semantics for case sensitivity but this is not the default behavior.
if (response["name"].str == baseName(path)){
// OneDrive 'name' matches local path name
log.vlog("The requested directory to create was found on OneDrive - skipping creating the directory: ", path );
// Check that this path is in the database
if (!itemdb.selectById(parent.driveId, parent.id, parent)){
// parent for 'path' is NOT in the database
log.vlog("The parent for this path is not in the local database - need to add parent to local database");
string parentPath = dirName(path);
uploadCreateDir(parentPath);
} else {
// parent is in database
log.vlog("The parent for this path is in the local database - adding requested path (", path ,") to database");
auto res = onedrive.getPathDetails(path);
saveItem(res);
}
} else {
// parent is in database
log.vlog("The parent for this path is in the local database - adding requested path (", path ,") to database");
auto res = onedrive.getPathDetails(path);
saveItem(res);
// They are the "same" name wise but different in case sensitivity
log.error("ERROR: Current directory has a 'case-insensitive match' to an existing directory on OneDrive");
log.error("ERROR: To resolve, rename this local directory: ", absolutePath(path));
log.log("Skipping: ", absolutePath(path));
return;
}
} else {
// They are the "same" name wise but different in case sensitivity
log.error("ERROR: Current directory has a 'case-insensitive match' to an existing directory on OneDrive");
log.error("ERROR: To resolve, rename this local directory: ", absolutePath(path));
// response is not valid JSON, an error was returned from OneDrive
log.error("ERROR: There was an error performing this operation on OneDrive");
log.error("ERROR: Increase logging verbosity to assist determining why.");
log.log("Skipping: ", absolutePath(path));
return;
}