commit 12ad74908740abc8f64a6d5394f1c3af06fd2732
parent 1ea80c4352ba787d96615a994fc7ca4c07a14eff
Author: Dan Stillman <dstillman@zotero.org>
Date: Wed, 8 Feb 2017 14:12:16 -0500
Fix additional file sync error with no remote stored hash
Follow-up to c9694e93b0
Diffstat:
2 files changed, 87 insertions(+), 68 deletions(-)
diff --git a/chrome/content/zotero/xpcom/storage/zfs.js b/chrome/content/zotero/xpcom/storage/zfs.js
@@ -412,6 +412,7 @@ Zotero.Sync.Storage.Mode.ZFS.prototype = {
}
delete headers["If-Match"];
headers["If-None-Match"] = "*";
+ storedHash = null;
Zotero.debug("Retrying with If-None-Match");
}
else {
@@ -728,7 +729,8 @@ Zotero.Sync.Storage.Mode.ZFS.prototype = {
successCodes: [204],
requestObserver: function (xmlhttp) {
request.setChannel(xmlhttp.channel);
- }
+ },
+ debug: true
}
);
}
diff --git a/test/tests/zfsTest.js b/test/tests/zfsTest.js
@@ -670,6 +670,90 @@ describe("Zotero.Sync.Storage.Mode.ZFS", function () {
assert.equal(item.attachmentSyncedHash, hash);
assert.equal(item.version, newVersion);
})
+
+
+ it("should retry with If-None-Match on 412 with missing remote hash", function* () {
+ var { engine, client, caller } = yield setup();
+ var zfs = new Zotero.Sync.Storage.Mode.ZFS({
+ apiClient: client
+ })
+
+ var file = getTestDataDirectory();
+ file.append('test.png');
+ var item = yield Zotero.Attachments.importFromFile({ file });
+ item.version = 5;
+ item.synced = true;
+ item.attachmentSyncedModificationTime = Date.now();
+ item.attachmentSyncedHash = 'bd4c33e03798a7e8bc0b46f8bda74fac'
+ yield item.saveTx();
+
+ var contentType = 'image/png';
+ var prefix = Zotero.Utilities.randomString();
+ var suffix = Zotero.Utilities.randomString();
+ var uploadKey = Zotero.Utilities.randomString(32, 'abcdef0123456789');
+
+ var called = 0;
+ // https://github.com/cjohansen/Sinon.JS/issues/607
+ let fixSinonBug = ";charset=utf-8";
+ server.respond(function (req) {
+ // Try with If-Match
+ if (req.method == "POST"
+ && req.url == `${baseURL}users/1/items/${item.key}/file`
+ && !req.requestBody.includes('upload=')
+ && req.requestHeaders["If-Match"] == item.attachmentSyncedHash) {
+ called++;
+ req.respond(
+ 412,
+ {
+ "Content-Type": "application/json"
+ },
+ "If-Match set but file does not exist"
+ );
+ }
+ // Retry with If-None-Match
+ else if (req.method == "POST"
+ && req.url == `${baseURL}users/1/items/${item.key}/file`
+ && !req.requestBody.includes('upload=')
+ && req.requestHeaders["If-None-Match"] == "*") {
+ assert.equal(called++, 1);
+ req.respond(
+ 200,
+ {
+ "Content-Type": "application/json"
+ },
+ JSON.stringify({
+ url: baseURL + "pretend-s3/1",
+ contentType: contentType,
+ prefix: prefix,
+ suffix: suffix,
+ uploadKey: uploadKey
+ })
+ );
+ }
+ // Upload file to S3
+ else if (req.method == "POST" && req.url == baseURL + "pretend-s3/1") {
+ assert.equal(called++, 2);
+ req.respond(201, {}, "");
+ }
+ // Use If-None-Match when registering upload
+ else if (req.method == "POST"
+ && req.url == `${baseURL}users/1/items/${item.key}/file`
+ && req.requestBody.includes('upload=')) {
+ assert.equal(called++, 3);
+ assert.equal(req.requestHeaders["If-None-Match"], "*");
+ req.respond(
+ 204,
+ {
+ "Last-Modified-Version": 10
+ },
+ ""
+ );
+ }
+ });
+
+ var result = yield engine.start();
+ assert.equal(called, 4);
+ });
})
@@ -819,73 +903,6 @@ describe("Zotero.Sync.Storage.Mode.ZFS", function () {
assert.isTrue(result.syncRequired);
});
- it("should retry with If-None-Match on 412 with missing remote hash", function* () {
- var { engine, client, caller } = yield setup();
- var zfs = new Zotero.Sync.Storage.Mode.ZFS({
- apiClient: client
- })
-
- var file = getTestDataDirectory();
- file.append('test.png');
- var item = yield Zotero.Attachments.importFromFile({ file });
- item.version = 5;
- item.synced = true;
- item.attachmentSyncedModificationTime = Date.now();
- item.attachmentSyncedHash = 'bd4c33e03798a7e8bc0b46f8bda74fac'
- yield item.saveTx();
-
- var contentType = 'image/png';
- var prefix = Zotero.Utilities.randomString();
- var suffix = Zotero.Utilities.randomString();
- var uploadKey = Zotero.Utilities.randomString(32, 'abcdef0123456789');
-
- var called = 0;
- server.respond(function (req) {
- if (req.method == "POST"
- && req.url == `${baseURL}users/1/items/${item.key}/file`
- && !req.requestBody.includes('upload=')
- && req.requestHeaders["If-Match"] == item.attachmentSyncedHash) {
- called++;
- req.respond(
- 412,
- {
- "Content-Type": "application/json"
- },
- "If-Match set but file does not exist"
- );
- }
- else if (req.method == "POST"
- && req.url == `${baseURL}users/1/items/${item.key}/file`
- && !req.requestBody.includes('upload=')
- && req.requestHeaders["If-None-Match"] == "*") {
- assert.equal(called++, 1)
- req.respond(
- 200,
- {
- "Content-Type": "application/json"
- },
- JSON.stringify({
- url: baseURL + "pretend-s3/1",
- contentType: contentType,
- prefix: prefix,
- suffix: suffix,
- uploadKey: uploadKey
- })
- );
- }
- })
-
- var stub = sinon.stub(zfs, "_uploadFile");
-
- yield zfs._processUploadFile({
- name: item.libraryKey
- });
-
- assert.equal(called, 2);
- assert.ok(stub.called);
-
- stub.restore();
- });
it("should handle 413 on quota limit", function* () {
var { engine, client, caller } = yield setup();