From 8298e5585c22174c7e0a9ea8c71696c48fb2af5c Mon Sep 17 00:00:00 2001 From: Tristan Cavelier <tristan.cavelier@tiolive.com> Date: Wed, 21 Aug 2013 15:48:35 +0200 Subject: [PATCH] jio tests replaced by new one --- test/jio/tests.js | 1164 +++++++++++++++++++++------------------------ 1 file changed, 548 insertions(+), 616 deletions(-) diff --git a/test/jio/tests.js b/test/jio/tests.js index db3c205..ff308f3 100644 --- a/test/jio/tests.js +++ b/test/jio/tests.js @@ -1,537 +1,408 @@ /*jslint indent: 2, maxlen: 80, nomen: true */ -/*global define, jIO, localStorage, window, test, ok, deepEqual, sinon, - expect */ +/*global define, window, exports, jIO, ok, module, test, expect, deepEqual, + sinon, FileReader, Blob, setTimeout */ -// define([module_name], [dependencies], module); (function (dependencies, module) { "use strict"; if (typeof define === 'function' && define.amd) { return define(dependencies, module); } if (typeof exports === 'object') { - return module(exports, require('jio')); + return module(exports, jIO); } window.jio_tests = {}; module(window.jio_tests, jIO); }(['exports', 'jio', 'sinon_qunit'], function (exports, jIO) { "use strict"; - var tmp; + var JIO = jIO.JIO, fakestorage = {}; - // localStorage cleanup - for (tmp in localStorage) { - if (localStorage.hasOwnProperty(tmp)) { - if (/^jio\//.test(tmp)) { - localStorage.removeItem(tmp); - } + ////////////////////////////////////////////////////////////////////////////// + // Fake Storage + + function FakeStorage(spec) { + this._id = spec.id; + if (typeof this._id !== 'string' || this._id.length <= 0) { + throw new TypeError( + "Initialization error: wrong id" + ); } } - ////////////////////////////////////////////////////////////////////////////// - // Tools - - function spyJioCallback(result_type, value, message) { - return function (err, response) { - var val; - switch (result_type) { - case 'value': - val = err || response; - break; - case 'status': - val = (err || {}).status; - break; - case 'jobstatus': - val = (err ? 'fail' : 'done'); - break; - default: - ok(false, "Unknown case " + result_type); - break; + FakeStorage.createNamespace = function ( + that, + method, + command, + param, + options + ) { + fakestorage[that._id + '/' + method] = { + param: param, + options: options, + success: function () { + command.success.apply(command, arguments); + delete fakestorage[that._id + '/' + method]; + }, + error: function () { + command.error.apply(command, arguments); + delete fakestorage[that._id + '/' + method]; + }, + retry: function () { + command.retry.apply(command, arguments); + delete fakestorage[that._id + '/' + method]; + }, + notify: function () { + command.notify.apply(command, arguments); + }, + storage: function () { + command.storage.apply(command, arguments); + }, + end: function () { + command.end.apply(command, arguments); + }, + commit: function () { + command.commit.apply(command, arguments); + }, + free: function () { + delete fakestorage[that._id + '/' + method]; } - deepEqual(val, value, message); }; - } - exports.spyJioCallback = spyJioCallback; - - // XXX docstring - function isUuid(uuid) { - var x = "[0-9a-fA-F]"; - if (typeof uuid !== "string") { - return false; - } - return (uuid.match( - "^" + x + "{8}-" + x + "{4}-" + - x + "{4}-" + x + "{4}-" + x + "{12}$" - ) === null ? false : true); - } - exports.isUuid = isUuid; - - // XXX docstring - exports.jsonlocalstorage = { - clear: function () { - return localStorage.clear(); - }, - getItem: function (item) { - var value = localStorage.getItem(item); - return value === null ? null : JSON.parse(value); - }, - setItem: function (item, value) { - return localStorage.setItem(item, JSON.stringify(value)); - }, - removeItem: function (item) { - return localStorage.removeItem(item); - } }; - function objectifyDocumentArray(array) { - var obj = {}, k; - for (k = 0; k < array.length; k += 1) { - obj[array[k]._id] = array[k]; - } - return obj; - } - - function closeAndcleanUpJio(jio) { - jio.close(); - exports.jsonlocalstorage.removeItem("jio/id/" + jio.getId()); - exports.jsonlocalstorage.removeItem("jio/job_array/" + jio.getId()); - } - exports.closeAndcleanUpJio = closeAndcleanUpJio; + FakeStorage.makeMethod = function (method) { + return function (command, param, options) { + FakeStorage.createNamespace(this, method, command, param, options); + }; + }; - function getJioLastJob(jio) { - return (exports.jsonlocalstorage.getItem( - "jio/job_array/" + jio.getId() - ) || [undefined]).pop(); - } + FakeStorage.prototype.post = FakeStorage.makeMethod('post'); + FakeStorage.prototype.put = FakeStorage.makeMethod('put'); + FakeStorage.prototype.get = FakeStorage.makeMethod('get'); + FakeStorage.prototype.remove = FakeStorage.makeMethod('remove'); + FakeStorage.prototype.putAttachment = FakeStorage.makeMethod('putAttachment'); + FakeStorage.prototype.getAttachment = FakeStorage.makeMethod('getAttachment'); + FakeStorage.prototype.removeAttachment = + FakeStorage.makeMethod('removeAttachment'); + FakeStorage.prototype.check = FakeStorage.makeMethod('check'); + FakeStorage.prototype.repair = FakeStorage.makeMethod('repair'); + FakeStorage.prototype.allDocs = FakeStorage.makeMethod('allDocs'); + + jIO.addStorage('fake', FakeStorage); + exports.fakestorage = fakestorage; ////////////////////////////////////////////////////////////////////////////// - // Compatibility - - function ospy(o, result_type, value, message, function_name) { - function_name = function_name || 'f'; - o[function_name] = function (err, response) { - var val; - switch (result_type) { - case 'value': - val = err || response; - break; - case 'status': - val = (err || {}).status; - break; - case 'jobstatus': - val = (err ? 'fail' : 'done'); - break; - default: - ok(false, "Unknown case " + result_type); - break; - } - deepEqual(val, value, message); - }; - sinon.spy(o, function_name); - } - exports.ospy = ospy; + // Tests - function otick(o, a, b) { - var tick = 10000, function_name = 'f'; - if (typeof a === 'number' && !isNaN(a)) { - tick = a; - a = b; - } - if (typeof a === 'string') { - function_name = a; - } - o.clock.tick(tick); - if (!o[function_name].calledOnce) { - if (o[function_name].called) { - ok(false, 'too much results'); - } else { - ok(false, 'no response'); - } - } - } - exports.otick = otick; + module('JIO'); - ////////////////////////////////////////////////////////////////////////////// - // Dummy Storage + /** + * Tests the instance initialization + */ + test('Init', function () { + expect(1); + var workspace = {}, jio = new JIO(undefined, { + "workspace": workspace + }); - // XX docstring - function dummyStorage(spec, my) { - var that = my.basicStorage(spec, my); + // tests if jio is an object + ok(typeof jio === 'object', 'Init ok!'); + }); - that._mode = spec.mode || 'normal'; - that._key = spec.key; - that._value = spec.value; + /** + * Tests a wrong command + */ + test('Wrong parameters', function () { + expect(2); + var result, jio = new JIO({ + "type": "fake", + "id": "Wrong para" + }, { + "workspace": {} + }); - if (that._mode === 'spec error') { - throw new TypeError( - "Initialization error set by the storage description." - ); + try { + jio.post(); // post(kwargs, [options], [callbacks]); + result = "No error thrown"; + } catch (e1) { + result = e1.name + ": " + e1.message; } + deepEqual( + result, + "TypeError: JIO().post(): Argument 1 is not of type 'object'", + "Wrong parameter" + ); - that.specToStore = function () { - return { - "mode": that._mode, - "key": that._key, - "value": that._value - }; - }; + try { + jio.allDocs(); // allDocs([options], [callbacks]); + result = "No error thrown"; + } catch (e2) { + result = e2.name + ": " + e2.message; + } + deepEqual(result, "No error thrown", "Good parameter"); + }); - that.post = function (command) { - setTimeout(function () { - var metadata = command.cloneDoc(), options = command.cloneOption(); - if (that._mode === 'no response') { - return; - } - // if (that._mode === 'no response + timeout reset') { - // return setTimeout(function () { - // command.resetTimeout(); - // }, that._value); - // } - if (that._mode === 'invalid error response') { - return that.error(); - } - if (that._mode === 'always fail') { - return that.error({ - "error": "conflict", - "message": "", - "reason": "unknown", - "status": 409, - "statusText": "Conflict" - }); - } - if (that._mode === 'post response no id') { - return that.success(); - } - that.success({"id": "document id a", "ok": true}); - }); - }; + /** + * Tests a storage initialization error + */ + test('Description Error', function () { + var clock, jio; + expect(2); + clock = sinon.useFakeTimers(); + jio = new JIO({ + "type": "blue" + }, { + "workspace": {} + }); - that.put = function (command) { - setTimeout(function () { - var metadata = command.cloneDoc(), options = command.cloneOption(); - if (that._mode === 'retry') { - if (!dummyStorage[that._key]) { - dummyStorage[that._key] = 0; - } - dummyStorage[that._key] += 1; - if (dummyStorage[that._key] === that._value) { - return that.success({"id": metadata._id, "ok": true}); - } - return that.retry(); - } - that.success({"id": metadata._id, "ok": true}); - }); - }; + // Tests wrong storage type + jio.post({}).always(function (answer) { + deepEqual(answer, { + "error": "internal_storage_error", + "message": "Check if the storage description respects the " + + "constraints provided by the storage designer. (TypeError: " + + "Unknown storage 'blue')", + "reason": "invalid description", + "status": 551, + "statusText": "Internal Storage Error" + }, "Unknown storage"); + }); + clock.tick(1); + + // Tests wrong storage description + jio = new JIO({ + "type": "fake", + "id": "" + }, { + "workspace": {} + }); - that.remove = function (command) { - setTimeout(function () { - var metadata = command.cloneDoc(), options = command.cloneOption(); - that.success({"id": metadata._id, "ok": true}); - }); - }; + jio.post({}).always(function (answer) { + deepEqual(answer, { + "error": "internal_storage_error", + "message": "Check if the storage description respects the " + + "constraints provided by the storage designer. (TypeError: " + + "Initialization error: wrong id)", + "reason": "invalid description", + "status": 551, + "statusText": "Internal Storage Error" + }, "Initialization error"); + }); + clock.tick(1); + }); - return that; - } + /** + * Tests a command which does not respond + */ + test('No Response or Response Timeout', function () { + var clock, jio, state; + expect(5); + clock = sinon.useFakeTimers(); + jio = new JIO({ + "type": "fake", + "id": "1 No Respons" + }, { + "workspace": {} + }); - jIO.addStorageType('dummy', dummyStorage); - exports.dummyStorage = dummyStorage; + // tests default timeout + jio.post({}).always(function (answer) { + deepEqual(answer, { + "error": "request_timeout", + "message": "Operation canceled after around " + + "10000 milliseconds of inactivity.", + "reason": "timeout", + "status": 408, + "statusText": "Request Timeout" + }, "Timeout error (default timeout)"); + }); + clock.tick(1); + clock.tick(10000); // wait 10 seconds + fakestorage['1 No Respons/post'].free(); + + jio = new JIO({ + "type": "fake", + "id": "2 No Respons" + }, { + "workspace": {} + }); - ////////////////////////////////////////////////////////////////////////////// - // Tests + // tests storage timeout + state = "Not called yet"; + jio.post({}).always(function (answer) { + state = "Called"; + deepEqual(answer, { + "error": "request_timeout", + "message": "Operation canceled after around " + + "10000 milliseconds of inactivity.", + "reason": "timeout", + "status": 408, + "statusText": "Request Timeout" + }, "Timeout error (storage timeout reset)"); + }); + clock.tick(1); + clock.tick(4999); // wait 5 seconds + fakestorage['2 No Respons/post'].notify(); + clock.tick(5000); // wait 5 seconds + deepEqual(state, "Not called yet", "Check callback state."); + clock.tick(5000); // wait 5 seconds + fakestorage['2 No Respons/post'].free(); + + jio = new JIO({ + "type": "fake", + "id": "3 No Respons" + }, { + "workspace": {}, + "default_timeout": 2 + }); - module("JIO"); + // tests jio option timeout + jio.post({}).always(function (answer) { + deepEqual(answer, { + "error": "request_timeout", + "message": "Operation canceled after around " + + "2 milliseconds of inactivity.", + "reason": "timeout", + "status": 408, + "statusText": "Request Timeout" + }, "Timeout error (specific default timeout)"); + }); + clock.tick(1); + clock.tick(1); + + // tests command option timeout + jio.post({}, {"timeout": 50}).always(function (answer) { + deepEqual(answer, { + "error": "request_timeout", + "message": "Operation canceled after around " + + "50 milliseconds of inactivity.", + "reason": "timeout", + "status": 408, + "statusText": "Request Timeout" + }, "Timeout error (command timeout)"); + }); + clock.tick(1); + clock.tick(49); + }); /** - * Tests the instance initialization + * Tests wrong responses */ - test('Instanciation', function () { - expect(1); - var jio = jIO.newJio(undefined); - - // tests if jio is an object - ok(typeof jio === 'object', 'Init ok!'); + test('Invalid Response', function () { + var clock, jio; + expect(2); + clock = sinon.useFakeTimers(); + jio = new JIO({ + "type": "fake", + "id": "1 Invalid Re" + }, { + "workspace": {} + }); - // checks the workspace - // XXX nothing to check for the moment, need to be implemented first + jio.post({}).always(function (answer) { + deepEqual(answer, { + "error": "internal_storage_error", + "message": "New document id have to be specified", + "reason": "invalid response", + "status": 551, + "statusText": "Internal Storage Error" + }, "Invalid Post Response"); + }); + clock.tick(1); + fakestorage['1 Invalid Re/post'].success(); + clock.tick(1); + + jio = new JIO({ + "type": "fake", + "id": "2 Invalid Re" + }, { + "workspace": {} + }); - closeAndcleanUpJio(jio); + jio.post({}).always(function (answer) { + deepEqual(answer, { + "error": "internal_storage_error", + "message": "Unknown status \"undefined\"", + "reason": "invalid response", + "status": 551, + "statusText": "Internal Storage Error" + }, "Invalid Post Error Response"); + }); + clock.tick(1); + fakestorage['2 Invalid Re/post'].error(); + clock.tick(1); }); - module("JIO Dummy Storage"); - - // XXX This will be uncommented when given parameters checking will be implem - // /** - // * Tests wrong commands - // */ - // test('Wrong parameters', function () { - // var result, jio = jIO.newJio({ - // "type": "dummy", - // "mode": "normal" - // }, { - // "workspace": {} - // }); - - // try { - // jio.post(); // post(kwargs, [options], [callbacks]); - // result = "No error thrown"; - // } catch (e1) { - // result = e1.name + ": " + e1.message; - // } - // deepEqual( - // result, - // "TypeError: JIO().post(): Argument 1 is not of type 'object'", - // "Wrong parameter" - // ); - - // try { - // jio.allDocs(); // allDocs([options], [callbacks]); - // result = "No error thrown"; - // } catch (e2) { - // result = e2.name + ": " + e2.message; - // } - // deepEqual(result, "No error thrown", "Good parameter"); - // }); - - // XXX this will be uncommented when validateState will be replaced by a - // simple `throw` in the storage init - // /** - // * Tests a storage initialization error - // */ - // test('Description Error', function () { - // var clock, jio; - // clock = sinon.useFakeTimers(); - // jio = jIO.newJio({ - // "type": "blue" - // }, { - // "workspace": {} - // }); - - // // Tests wrong storage type - // jio.post({}).always(function (answer) { - // deepEqual(answer, { - // "error": "internal_storage_error", - // "message": "Check if the storage description respects the " + - // "constraints provided by the storage designer. (TypeError: " + - // "Unknown storage 'blue')", - // "reason": "invalid description", - // "status": 551, - // "statusText": "Internal Storage Error" - // }, "Unknown storage"); - // }); - // clock.tick(1); - - // // Tests wrong storage description - // jio = jIO.newJio({ - // "type": "dummy", - // "mode": "spec error" - // }, { - // "workspace": {} - // }); - - // jio.post({}).always(function (answer) { - // deepEqual(answer, { - // "error": "internal_storage_error", - // "message": "Check if the storage description respects the " + - // "constraints provided by the storage designer. (TypeError: " + - // "Initialization error set by the storage description.)", - // "reason": "invalid description", - // "status": 551, - // "statusText": "Internal Storage Error" - // }, "Initialization error"); - // }); - // clock.tick(1); - // }); - - - // XXX timeout is not implemented yet - // /** - // * Tests a command which does not respond - // */ - // test('No Response or Response Timeout', function () { - // var clock, jio, state; - // expect(5); - // clock = sinon.useFakeTimers(); - // jio = jIO.newJio({ - // "type": "dummy", - // "mode": "no response" - // }, { - // "workspace": {} - // }); - - // // tests with default timeout - // jio.post({}).always(function (answer) { - // deepEqual(answer, { - // "error": "request_timeout", - // "message": "Operation canceled after around 10000 milliseconds.", - // "reason": "timeout", - // "status": 408, - // "statusText": "Request Timeout" - // }, "Timeout error (default timeout)"); - // }); - // clock.tick(10000); // wait 10 seconds - - // jio = jIO.newJio({ - // "type": "dummy", - // "mode": "no response + timeout reset", - // "value": 5000 // reset after 5 seconds - // }, { - // "workspace": {} - // }); - - // // tests with storage timeout extension - // state = "Not called yet"; - // jio.post({}).always(function (answer) { - // state = "Called"; - // deepEqual(answer, { - // "error": "request_timeout", - // "message": "Operation canceled after around 15000 milliseconds.", - // "reason": "timeout", - // "status": 408, - // "statusText": "Request Timeout" - // }, "Timeout error (storage timeout reset)"); - // }); - // clock.tick(10000); // wait 10 seconds - // deepEqual(state, "Not called yet", "Check callback state."); - // clock.tick(5000); // wait 5 seconds - - // jio = jIO.newJio({ - // "type": "dummy", - // "mode": "no response" - // }, { - // "workspace": {}, - // "default_timeout": 2 - // }); - - // // tests with jio option timeout - // jio.post({}).always(function (answer) { - // deepEqual(answer, { - // "error": "request_timeout", - // "message": "Operation canceled after around 2 milliseconds.", - // "reason": "timeout", - // "status": 408, - // "statusText": "Request Timeout" - // }, "Timeout error (specific default timeout)"); - // }); - // clock.tick(2); - - // // tests with command option timeout - // jio.post({}, {"timeout": 50}).always(function (answer) { - // deepEqual(answer, { - // "error": "request_timeout", - // "message": "Operation canceled after around 50 milliseconds.", - // "reason": "timeout", - // "status": 408, - // "statusText": "Request Timeout" - // }, "Timeout error (command timeout)"); - // }); - // clock.tick(50); - // }); - - // /** - // * Tests wrong responses - // */ - // test('Invalid Response', function () { - // var clock, jio; - // clock = sinon.useFakeTimers(); - // jio = jIO.newJio({ - // "type": "dummy", - // "mode": "post response no id" - // }); - - // jio.post({}, function (err, response) { - // deepEqual(err || response, { - // "error": "internal_storage_error", - // "message": "New document id have to be specified", - // "reason": "invalid response", - // "status": 551, - // "statusText": "Internal Storage Error" - // }, "Invalid Post Response"); - // }); - // clock.tick(1000); - - // closeAndcleanUpJio(jio); - - // jio = jIO.newJio({ - // "type": "dummy", - // "mode": "invalid error response" - // }); - - // jio.post({}, function (err, response) { - // deepEqual(err || response, { - // "error": "internal_storage_error", - // "message": "Unknown status \"undefined\"", - // "reason": "invalid response", - // "status": 551, - // "statusText": "Internal Storage Error" - // }, "Invalid Post Error Response"); - // }); - // clock.tick(1000); - - // closeAndcleanUpJio(jio); - // }); - /** - * Tests a valid responses + * Tests valid responses */ test('Valid Responses & Callbacks', function () { - expect(4); - var clock, jio, message; + var clock, jio, o = {}; + expect(7); clock = sinon.useFakeTimers(); - jio = jIO.newJio({ - "type": "dummy", - "mode": "normal" + jio = new JIO({ + "type": "fake", + "id": "Valid Resp" + }, { + "workspace": {} }); // Tests post command callbacks post(metadata).always(onResponse) + // valid response. - message = "Post Command: post(metadata).always(function (answer) {..}) + " + - "valid response."; - jio.post({}, function (err, response) { - deepEqual(err || response, { + o.message = "Post Command: post(metadata).always(function (answer) {..}) " + + "+ valid response."; + jio.post({}).always(function (answer) { + deepEqual(answer, { "ok": true, - "id": "document id a" - }, message); + "id": "document id a", + "status": 201, + "statusText": "Created" + }, o.message); }); - clock.tick(1000); + clock.tick(1); + fakestorage['Valid Resp/post'].success({"id": "document id a"}); + clock.tick(1); // Tests post command callbacks post(metadata).done(onSuccess).fail(onError) - message = "Post Command: post(metadata).done(function (answer) {..})." + + o.message = "Post Command: post(metadata).done(function (answer) {..})." + "fail(function (answer) {..})"; - jio.post({}, function (answer) { + jio.post({}).done(function (answer) { deepEqual(answer, { "ok": true, - "id": "document id a" - }, message); - }, function (answer) { - deepEqual(answer, "Should not fail", message); + "id": "document id a", + "status": 201, + "statusText": "Created" + }, o.message); + }).fail(function (answer) { + deepEqual(answer, "Should not fail", o.message); }); - clock.tick(1000); + clock.tick(1); + fakestorage['Valid Resp/post'].success({"id": "document id a"}); + clock.tick(1); // Tests post command callbacks post(metadata, onResponse) - message = "Post Command: post(metadata, function (err, response) {..})"; + o.message = "Post Command: post(metadata, function (err, response) {..})"; jio.post({}, function (err, response) { if (err) { - return deepEqual(err, "Should not fail", message); + return deepEqual(err, "Should not fail", o.message); } deepEqual(response, { "ok": true, - "id": "document id a" - }, message); + "id": "document id a", + "status": 201, + "statusText": "Created" + }, o.message); }); - clock.tick(1000); - - closeAndcleanUpJio(jio); + clock.tick(1); + fakestorage['Valid Resp/post'].success({"id": "document id a"}); + clock.tick(1); // Tests post command callbacks post(metadata, onSuccess, onError) + error // response. - message = "Post Command: post(metadata, function (response) {..}, " + + o.message = "Post Command: post(metadata, function (response) {..}, " + "function (err) {..}) + valid error response."; - jio = jIO.newJio({ - "type": "dummy", - "mode": "always fail" - }); jio.post({}, function (response) { - deepEqual(response, "Should fail", message); + deepEqual(response, "Should fail", o.message); }, function (err) { deepEqual(err, { "status": 409, @@ -539,183 +410,244 @@ "error": "conflict", "reason": "unknown", "message": "" - }, message); + }, o.message); }); - clock.tick(1000); - - closeAndcleanUpJio(jio); - }); - - module("JIO Job Management"); - - test("Several Jobs at the same time", function () { - expect(3); - var clock = sinon.useFakeTimers(), jio = jIO.newJio({"type": "dummy"}); - - jio.put({"_id": "file1", "title": "t1"}, spyJioCallback('value', { - "ok": true, - "id": "file1" - }, "job1")); - jio.put({"_id": "file2", "title": "t2"}, spyJioCallback('value', { - "ok": true, - "id": "file2" - }, "job2")); - jio.put({"_id": "file3", "title": "t3"}, spyJioCallback('value', { - "ok": true, - "id": "file3" - }, "job3")); - clock.tick(1000); - - closeAndcleanUpJio(jio); - }); + clock.tick(1); + fakestorage['Valid Resp/post'].error('conflict'); + clock.tick(1); + + // Tests getAttachment command string response + jio.getAttachment({"_id": "a", "_attachment": "b"}). + always(function (answer) { + ok(answer instanceof Blob, "Get Attachment Command: Blob returned"); + }); + clock.tick(1); + fakestorage['Valid Resp/getAttachment'].success("document id a"); + clock.tick(1); + + // Tests notify responses + o.notified = true; + o.message = "Synchronous Notify"; + jio.post({}).progress(function (answer) { + deepEqual(answer, o.answer, o.message); + }); + clock.tick(1); + o.answer = undefined; + fakestorage['Valid Resp/post'].notify(); + o.answer = 'hoo'; + fakestorage['Valid Resp/post'].notify(o.answer); + o.answer = 'Forbidden!!!'; + o.message = 'Notification forbidden after success'; + setTimeout(fakestorage['Valid Resp/post'].notify, 2); + fakestorage['Valid Resp/post'].success(); + clock.tick(2); - test("Similar Jobs at the same time (Update)", function () { - expect(8); - var clock = sinon.useFakeTimers(), jio = jIO.newJio({"type": "dummy"}); - function compareResults(err, response) { - deepEqual(err || response, {"id": "file", "ok": true}, "job ok"); - } - jio.put({"_id": "file", "title": "t"}, compareResults); - jio.put({"_id": "file", "title": "t"}, compareResults); - jio.put({"_id": "file", "title": "t"}, compareResults); - deepEqual(getJioLastJob(jio).id, 1, "Check job queue"); - clock.tick(1000); - - jio.put({"_id": "file", "content": "content"}, compareResults); - jio.remove({"_id": "file", "content": "content"}, compareResults); - jio.put({"_id": "file", "content": "content"}, compareResults); - deepEqual(getJioLastJob(jio).id, 5, "Check job queue"); - clock.tick(10000); - - closeAndcleanUpJio(jio); }); - test("Same document jobs at the same time (Wait for job(s))", function () { - expect(6); - var clock = sinon.useFakeTimers(), jio = jIO.newJio({"type": "dummy"}); - - function compareResults(err, response) { - deepEqual(err || response, {"id": "file", "ok": true}, "job ok"); - } + /** + * Tests metadata values + */ + test('Metadata values', function () { + expect(9); + var o, clock = sinon.useFakeTimers(), jio = new JIO({ + "type": "fake", + "id": "Metadata v" + }, { + "workspace": {} + }); - jio.put({"_id": "file", "content": "content"}, compareResults); - deepEqual( - getJioLastJob(jio).status.waitforjob, - undefined, - "Job 1 is not waiting for someone" - ); + o = {}; + + o.request = { + "_id": undefined, + "number": -13, + "date": new Date(0), + "boolean": true, + "array": ['a'], + "long_array": ['a', 'b'], + "object": {'content': 'c'}, + "long_object": {'content': 'd', "scheme": "e"}, + "toJSON": {toJSON: function () { + return 'hey!'; + }}, + "null": null, + "undefined": undefined, + "invalid_date": new Date('aoeuh'), + "not_finite": Infinity, + "empty_array": [], + "empty_object": {}, + "no_content_object": {"e": "f"}, + "wrong_array": [{}, null, {"blue": "green"}] + }; - jio.remove({"_id": "file", "content": "content"}, compareResults); - deepEqual( - getJioLastJob(jio).status.waitforjob, - [1], - "Job 2 is wainting for 1" - ); + o.response = { + "number": -13, + "date": new Date(0).toJSON(), + "boolean": true, + "array": "a", + "long_array": ["a", "b"], + "object": "c", + "long_object": {"content": "d", "scheme": "e"}, + "toJSON": "hey!" + }; - jio.put({"_id": "file"}, compareResults); + jio.post(o.request); + clock.tick(1); deepEqual( - getJioLastJob(jio).status.waitforjob, - [1, 2], - "Job 3 is waiting for 1 and 2" + fakestorage["Metadata v/post"].param, + o.response, + "Post" ); - - clock.tick(1000); - - closeAndcleanUpJio(jio); - }); - - test("Server will be available soon (Wait for time)", function () { - expect(2); - var clock = sinon.useFakeTimers(), jio; - jio = jIO.newJio({ - "type": "dummy", - "mode": "retry", - "key": "035139054", - "value": 3 + fakestorage["Metadata v/post"].success(); + clock.tick(1); + + o.request._id = 'a'; + o.response._id = 'a'; + jio.put(o.request); + clock.tick(1); + deepEqual(fakestorage["Metadata v/put"].param, o.response, "Put"); + fakestorage["Metadata v/put"].success(); + clock.tick(1); + + jio.get({ + "_id": "a" }); - jio.put( - {"_id": "file", "content": "content"}, - {"max_retry": 3}, - function (err, response) { - deepEqual(err || response, {"id": "file", "ok": true}, "Job ok"); - } - ); - clock.tick(2000); - - deepEqual(dummyStorage['035139054'], 3, "tried 3 times"); - delete dummyStorage['035139054']; - - closeAndcleanUpJio(jio); - }); - - test("Restore old Jio", function () { - - var o = { - clock: sinon.useFakeTimers(), - spy: ospy, - tick: otick + clock.tick(1); + deepEqual(fakestorage["Metadata v/get"].param, { + "_id": "a" + }, "Get"); + fakestorage["Metadata v/get"].success(); + clock.tick(1); + + jio.remove({ + "_id": "a" + }); + clock.tick(1); + deepEqual(fakestorage["Metadata v/remove"].param, { + "_id": "a" + }, "Remove"); + fakestorage["Metadata v/remove"].success(); + clock.tick(1); + + jio.allDocs(); + clock.tick(1); + deepEqual(fakestorage["Metadata v/allDocs"].param, {}, "AllDocs"); + fakestorage["Metadata v/allDocs"].success(); + clock.tick(1); + + o.request = { + "_id": "a", + "_attachment": "body", + "_data": "b", + "_mimetype": "c" }; + jio.putAttachment(o.request); + clock.tick(1); + ok(fakestorage["Metadata v/putAttachment"].param._blob instanceof Blob, + "Put Attachment + check blob"); + deepEqual([ + fakestorage["Metadata v/putAttachment"].param._id, + fakestorage["Metadata v/putAttachment"].param._attachment + ], ["a", "body"], "Put Attachment + check ids"); + fakestorage["Metadata v/putAttachment"].success(); + clock.tick(1); + + o.request._blob = new Blob(['d'], {"type": "e"}); + delete o.request._mimetype; + delete o.request._data; + jio.putAttachment(o.request); + clock.tick(1); + ok(fakestorage["Metadata v/putAttachment"].param._blob === o.request._blob, + "Put Attachment with blob + check blob"); + deepEqual([ + fakestorage["Metadata v/putAttachment"].param._id, + fakestorage["Metadata v/putAttachment"].param._attachment + ], ["a", "body"], "Put Attachment with blob + check ids"); + fakestorage["Metadata v/putAttachment"].success(); + clock.tick(1); + }); - function waitUntilLastJobIs(state) { - while (true) { - if (getJioLastJob(o.jio) === undefined) { - ok(false, "No job have state: " + state); - break; - } - if (getJioLastJob(o.jio).status.label === state) { - break; - } - o.clock.tick(25); - } - } - - function waitUntilAJobExists(timeout) { - var cpt = 0, job = false; - while (true) { - if (getJioLastJob(o.jio) !== undefined) { - job = true; - break; - } - if (cpt >= timeout) { - break; - } - o.clock.tick(25); - cpt += 25; - } - ok(job, "Wait until a job is created"); - } + /** + * Tests job retry + */ + test("Job Retry", function () { + var clock, jio, state; + expect(4); + clock = sinon.useFakeTimers(); - o.jio = jIO.newJio({ - "type": "dummy", - "mode": "retry", - "key": "12314", - "value": 3 + jio = new JIO({ + "type": "fake", + "id": "1 Job Retry" + }, { + "workspace": {} }); - o.jio_id = o.jio.getId(); - - o.jio.put({"_id": "file", "title": "myFile"}, {"max_retry": 3}, o.f); - waitUntilLastJobIs("initial"); // "on going" or "wait" should work - // xxx also test with waitUntilLastJobIs("on going") ? - o.jio.close(); - - o.jio = jIO.newJio({ - "type": "dummy", - "mode": "retry", - "key": "12314", - "value": 3 + state = "Not called yet"; + jio.get({"_id": "a"}).always(function (answer) { + state = "Called"; + deepEqual(answer, { + "error": "internal_server_error", + "message": "", + "reason": "unknown", + "status": 500, + "statusText": "Internal Server Error" + }, "Error response"); }); - waitUntilAJobExists(30000); // timeout 30 sec + clock.tick(1); + fakestorage['1 Job Retry/get'].retry('internal_server_error'); + clock.tick(1); + deepEqual(state, "Not called yet", "Check callback state."); + + clock.tick(1999); + fakestorage['1 Job Retry/get'].retry('internal_server_error'); + clock.tick(1); + deepEqual(state, "Not called yet", "Check callback state."); + + clock.tick(3999); + fakestorage['1 Job Retry/get'].retry('internal_server_error'); + clock.tick(1); + deepEqual(state, "Called", "Check callback state."); + }); - deepEqual(getJioLastJob(o.jio).command.label, 'put', 'Job restored'); - o.clock.tick(2000); - ok(getJioLastJob(o.jio) === undefined, "Job executed"); - o.clock.tick(1000); + /** + * Tests job workspace + */ + test("Job Workspace", function () { + var workspace = {}, clock, jio; + expect(2); - exports.jsonlocalstorage.removeItem("jio/id/" + o.jio_id); - exports.jsonlocalstorage.removeItem("jio/job_array/" + o.jio_id); - closeAndcleanUpJio(o.jio); + clock = sinon.useFakeTimers(); + jio = new JIO({ + "type": "fake", + "id": "1 Job Worksp" + }, { + "workspace": workspace + }); + jio.get({"_id": "a"}, {"max_retry": 2, "timeout": 12}); + + deepEqual(workspace, { + "jio/jobs/{\"id\":\"1 Job Worksp\",\"type\":\"fake\"}": jIO.util. + uniqueJSONStringify([{ + "kwargs": {"_id": "a"}, + "options": {"max_retry": 2, "timeout": 12}, + "storage_spec": {"type": "fake", "id": "1 Job Worksp"}, + "method": "get", + "created": new Date(0), + "tried": 1, + "state": "running", + "modified": new Date(0), + "max_retry": 2, + "timeout": 12, + "id": 1 + }]) + }, 'Check workspace'); + + clock.tick(1); + fakestorage["1 Job Worksp/get"].success({"_id": "a", "b": "c"}); + clock.tick(1); + + deepEqual(workspace, {}, 'Check workspace'); }); })); -- 2.30.9