Identify initial chunk of an upload so as to be more resilient

This commit is contained in:
Simon Walton 2018-11-19 15:26:08 -08:00
parent 2d2cc0eaca
commit 2a7e22bf31
2 changed files with 22 additions and 4 deletions

View file

@ -43,7 +43,13 @@ $(document).ready(function(){
var chunk = file.slice(offset, offset + nextChunkSize, file.type);
var chunkFormData = new FormData();
var formItemName = isFinal ? 'restore-file-chunk-final' : 'restore-file-chunk';
var formItemName = 'restore-file-chunk';
if (offset == 0) {
formItemName = isFinal ? 'restore-file-chunk-only' : 'restore-file-chunk-initial';
} else if (isFinal) {
formItemName = 'restore-file-chunk-final';
}
chunkFormData.append(formItemName, chunk, filename);
var ajaxParams = {
url: '/content/upload',
@ -57,7 +63,7 @@ $(document).ready(function(){
};
var ajaxObject = $.ajax(ajaxParams);
ajaxObject.fail(function(jqXHR, textStatus, errorThrown) {
ajaxObject.fail(function (jqXHR, textStatus, errorThrown) {
showErrorMessage(
"Error",
"There was a problem restoring domain content.\n"

View file

@ -2523,12 +2523,20 @@ bool DomainServer::processPendingContent(HTTPConnection* connection, QString ite
QByteArray sessionIdBytes = connection->requestHeader(UPLOAD_SESSION_KEY);
int sessionId = sessionIdBytes.toInt();
bool newUpload = itemName == "restore-file" || itemName == "restore-file-chunk-initial" || itemName == "restore-file-chunk-only";
if (filename.endsWith(".zip", Qt::CaseInsensitive)) {
static const QString TEMPORARY_CONTENT_FILEPATH { QDir::tempPath() + "/hifiUploadContent_XXXXXX.zip" };
if (_pendingContentFiles.find(sessionId) == _pendingContentFiles.end()) {
if (!newUpload) {
return false;
}
std::unique_ptr<QTemporaryFile> newTemp(new QTemporaryFile(TEMPORARY_CONTENT_FILEPATH));
_pendingContentFiles[sessionId] = std::move(newTemp);
} else if (newUpload) {
qCDebug(domain_server) << "New upload received using existing session ID";
_pendingContentFiles[sessionId]->resize(0);
}
QTemporaryFile& _pendingFileContent = *_pendingContentFiles[sessionId];
@ -2543,7 +2551,7 @@ bool DomainServer::processPendingContent(HTTPConnection* connection, QString ite
// Respond immediately - will timeout if we wait for restore.
connection->respond(HTTPConnection::StatusCode200);
if (itemName == "restore-file-chunk-final" || itemName == "restore-file") {
if (itemName == "restore-file" || itemName == "restore-file-chunk-final" || itemName == "restore-file-chunk-only") {
auto deferred = makePromise("recoverFromUploadedBackup");
deferred->then([this, sessionId](QString error, QVariantMap result) {
@ -2554,11 +2562,15 @@ bool DomainServer::processPendingContent(HTTPConnection* connection, QString ite
}
} else if (filename.endsWith(".json", Qt::CaseInsensitive)
|| filename.endsWith(".json.gz", Qt::CaseInsensitive)) {
if (_pendingUploadedContents.find(sessionId) == _pendingUploadedContents.end() && !newUpload) {
qCDebug(domain_server) << "Json upload with invalid session ID received";
return false;
}
QByteArray& _pendingUploadedContent = _pendingUploadedContents[sessionId];
_pendingUploadedContent += dataChunk;
connection->respond(HTTPConnection::StatusCode200);
if (itemName == "restore-file-chunk-final" || itemName == "restore-file") {
if (itemName == "restore-file" || itemName == "restore-file-chunk-final" || itemName == "restore-file-chunk-only") {
// invoke our method to hand the new octree file off to the octree server
QMetaObject::invokeMethod(this, "handleOctreeFileReplacement",
Qt::QueuedConnection, Q_ARG(QByteArray, _pendingUploadedContent));