Attempting to upload large files. The regular upload method works without an issue. When I try to use appendV2 and Finish I get that the offset was incorrect and the correct offset. This post does discuss how to do offsets but want to make it clearer.
From the docs. "Offset in bytes at which data should be appended. We use this to make sure upload data isn’t lost or duplicated in the event of a network error."
If I have a file with looping "abcd" * 13*1024*1024 it would give me a 54525952 Bytes or 54.5MB. My chunk size is 4MB (4194304 Bytes).
For this file I would start the upload with the full file .uploadSessionStart(input: abcdFileURL). The initial offset should be my chunksize. My cursor would be .UploadSessionCursor(sessionId, offset) and the append would be .uploadSessionAppendV2(cursor, input: abcdFileURL). Every append after should increment the offset by the chunksize, 4MB, 8MB ... 50MB, until the last offset is equal to or less than the chunksize. This would be the final file size in the finish. Which would be .uploadSessionFinish(cursor(sessionId, fileSize), input: abcdFileSize)
Does that sound correct logically how it should work?
When I attempt this I get that the offset should be the file size for append. When I test if the file is less than 150MB and set offset to file size with the start/append/finish (so that it basically acts like the regular .upload) it works.
Output when using normal append with increasing offset.
Offset Append Value: 155189248
difference 12582912
Offset Append Value: 159383552
difference 8388608
Offset Finish Value: 167772160
File Size: 167772160
Error appending data to file upload session: [request-id 3415da207401412eaf901ef5aef245a8] API route error - {
".tag" = "incorrect_offset";
"correct_offset" = 167772160;
}
Error appending data to file upload session: sessionTaskFailed(error: Error Domain=NSURLErrorDomain Code=-1001 "The request timed out." UserInfo={_kCFStreamErrorCodeKey=-2102, NSUnderlyingError=0x6000023d7d50 {Error Domain=kCFErrorDomainCFNetwork Code=-1001 "(null)" UserInfo={_kCFStreamErrorCodeKey=-2102, _kCFStreamErrorDomainKey=4}}, _NSURLErrorFailingURLSessionTaskErrorKey=LocalUploadTask <7490F290-DA4A-49A9-AA00-B378E94A46E0>.<35>, _NSURLErrorRelatedURLSessionTaskErrorKey=(
"LocalUploadTask <7490F290-DA4A-49A9-AA00-B378E94A46E0>.<35>"
), NSLocalizedDescription=The request timed out., NSErrorFailingURLStringKey=https://api-content.dropbox.com/2/files/upload_session/append_v2, NSErrorFailingURLKey=https://api-content.dropbox.com/2/files/upload_session/append_v2, _kCFStreamErrorDomainKey=4})2023-04-20 19:57:32.228273-0600 cloud-tools[61893:1384752] Task <C348ACD5-53C3-4908-9511-697D5FB68DEF>.<44> finished with error [-1001] Error Domain=NSURLErrorDomain Code=-1001 "The request timed out." UserInfo={_kCFStreamErrorCodeKey=-2102, NSUnderlyingError=0x6000023d54d0 {Error Domain=kCFErrorDomainCFNetwork Code=-1001 "(null)" UserInfo={_kCFStreamErrorCodeKey=-210
2, _kCFStreamErrorDomainKey=4}}, _NSURLErrorFailingURLSessionTaskErrorKey=LocalUploadTask <C348ACD5-53C3-4908-9511-697D5FB68DEF>.<44>, _NSURLErrorRelatedURLSessionTaskErrorKey=(
"LocalUploadTask <C348ACD5-53C3-4908-9511-697D5FB68DEF>.<44>"
), NSLocalizedDescription=The request timed out., NSErrorFailingURLStringKey=https://api-content.dropbox.com/2/files/upload_session/append_v2, NSErrorFailingURLKey=https://api-content.dropbox.com/2/files/upload_session/append_v2, _kCFStreamErrorDomainKey=4}
Output where I set the offset to the file size if less than 150MB.
Offset Finish Value: 54525952
File Size: 54525952
Finish Good: {
"client_modified" = "2023-04-21T01:39:37Z";
"content_hash" = 9fd01c7cc2807ed423dbd11a1a06b9fd77ad15e843fcbabf4f363da527e06175;
id = "id:992ScyV19hQAAAAAAAAHbA";
"is_downloadable" = 1;
name = "testjamf.txt";
"path_display" = "/testfile.txt";
"path_lower" = "/testfile.txt";
rev = 5f9cebae50714a5e0ed31;
"server_modified" = "2023-04-21T01:39:37Z";
size = 109051904;
}My code that produces the errors.
dbxClient.files.uploadSessionStart(input: fileURL)
.response(completionHandler: { [self] response, error in
if let result = response {
print(result)
var offset: UInt64 = chunkSize
//Append chunks to file
while (offset < fileSize!) {
if ((fileSize! - offset) <= chunkSize) {
print("Offset Value: \(offset)")
dbxClient.files.uploadSessionFinish(cursor: Files.UploadSessionCursor(sessionId: result.sessionId, offset: fileSize!), commit: Files.CommitInfo(path: dbFilePath), input: fileURL)
.response { response, error in
if let result = response {
print("Finish Good: \(result)")
} else {
print("Finish Error: \(error!)")
}
}
offset = fileSize!
} else {
print("Offset Value: \(offset)")
dbxClient.files.uploadSessionAppendV2(cursor: Files.UploadSessionCursor(sessionId: result.sessionId, offset: offset), input: fileURL)
.response {response , error in
if let response = response {
print("File appended: \(response)")
} else {
print("Error appending data to file upload session: \(error!)")
}
}
// .progress { progressData in print(progressData) }
offset += chunkSize
}
}
} else {
// the call failed
print(error!)
}
})
}