1
0
Fork 0
arangodb/js/common/tests/replication.js

3153 lines
99 KiB
JavaScript

/*jslint indent: 2, nomen: true, maxlen: 80 */
/*global require, assertEqual, assertTrue */
////////////////////////////////////////////////////////////////////////////////
/// @brief test the replication functions
///
/// @file
///
/// DISCLAIMER
///
/// Copyright 2010-2012 triagens GmbH, Cologne, Germany
///
/// Licensed under the Apache License, Version 2.0 (the "License");
/// you may not use this file except in compliance with the License.
/// You may obtain a copy of the License at
///
/// http://www.apache.org/licenses/LICENSE-2.0
///
/// Unless required by applicable law or agreed to in writing, software
/// distributed under the License is distributed on an "AS IS" BASIS,
/// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
/// See the License for the specific language governing permissions and
/// limitations under the License.
///
/// Copyright holder is triAGENS GmbH, Cologne, Germany
///
/// @author Jan Steemann
/// @author Copyright 2013, triAGENS GmbH, Cologne, Germany
////////////////////////////////////////////////////////////////////////////////
var jsunity = require("jsunity");
var arangodb = require("org/arangodb");
var errors = arangodb.errors;
var db = arangodb.db;
var internal = require("internal");
var replication = require("org/arangodb/replication");
// -----------------------------------------------------------------------------
// --SECTION-- replication logger test
// -----------------------------------------------------------------------------
////////////////////////////////////////////////////////////////////////////////
/// @brief test suite
////////////////////////////////////////////////////////////////////////////////
function ReplicationLoggerSuite () {
var cn = "UnitTestsReplication";
var cn2 = "UnitTestsReplication2";
var getLogEntries = function () {
return db._collection('_replication').count();
};
var getLastLogEntry = function (count) {
if (count) {
return db._collection('_replication').last(count);
}
return db._collection('_replication').last();
};
var compareTicks = function (l, r) {
if (l.length != r.length) {
return l.length - r.length < 0 ? -1 : 1;
}
// length is equal
for (i = 0; i < l.length; ++i) {
if (l[i] != r[i]) {
return l[i] < r[i] ? -1 : 1;
}
}
return 0;
};
return {
////////////////////////////////////////////////////////////////////////////////
/// @brief set up
////////////////////////////////////////////////////////////////////////////////
setUp : function () {
replication.logger.properties({ maxEvents: 1048576 });
},
////////////////////////////////////////////////////////////////////////////////
/// @brief tear down
////////////////////////////////////////////////////////////////////////////////
tearDown : function () {
replication.logger.stop();
replication.logger.properties({ maxEvents: 1048576 });
db._drop(cn);
db._drop(cn2);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief start logger
////////////////////////////////////////////////////////////////////////////////
testStartLogger : function () {
var actual, state;
// start
actual = replication.logger.start();
assertTrue(actual);
state = replication.logger.state().state;
assertTrue(state.running);
assertTrue(typeof state.lastLogTick === 'string');
assertMatch(/^\d+$/, state.lastLogTick);
assertTrue(state.totalEvents >= 1);
// start again
actual = replication.logger.start();
assertTrue(actual);
var entry = getLastLogEntry();
assertEqual(1001, entry.type);
entry = JSON.parse(entry.data);
assertMatch(/^\d+$/, entry.lastTick);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief stop logger
////////////////////////////////////////////////////////////////////////////////
testStopLogger : function () {
var actual, state;
// start
actual = replication.logger.start();
assertTrue(actual);
state = replication.logger.state().state;
assertTrue(state.running);
assertTrue(typeof state.lastLogTick === 'string');
assertMatch(/^\d+$/, state.lastLogTick);
assertTrue(state.totalEvents >= 1);
// stop
actual = replication.logger.stop();
assertTrue(actual);
state = replication.logger.state().state;
assertFalse(state.running);
assertTrue(typeof state.lastLogTick === 'string');
assertMatch(/^\d+$/, state.lastLogTick);
assertTrue(state.totalEvents >= 2);
var entry = getLastLogEntry();
assertEqual(1000, entry.type);
entry = JSON.parse(entry.data);
assertMatch(/^\d+$/, entry.lastTick);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief get state
////////////////////////////////////////////////////////////////////////////////
testGetLoggerState : function () {
var state, tick, server, clients;
state = replication.logger.state().state;
assertFalse(state.running);
tick = state.lastLogTick;
assertTrue(typeof tick === 'string');
assertNotEqual("", state.time);
assertMatch(/^\d+-\d+-\d+T\d+:\d+:\d+Z$/, state.time);
state = replication.logger.state().state;
assertFalse(state.running);
assertEqual(tick, state.lastLogTick);
assertTrue(typeof state.lastLogTick === 'string');
assertMatch(/^\d+$/, state.lastLogTick);
assertTrue(state.totalEvents >= 0);
server = replication.logger.state().server;
assertEqual(server.version, db._version());
assertNotEqual("", server.serverId);
assertMatch(/^\d+$/, server.serverId);
clients = replication.logger.state().clients;
assertTrue(Array.isArray(clients));
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test logging disabled
////////////////////////////////////////////////////////////////////////////////
testDisabledLogger : function () {
var state, tick;
state = replication.logger.state().state;
assertFalse(state.running);
tick = state.lastLogTick;
assertTrue(typeof tick === 'string');
assertMatch(/^\d+$/, state.lastLogTick);
assertTrue(state.totalEvents >= 0);
// do something that will cause logging (if it was enabled...)
var c = db._create(cn);
c.save({ "test" : 1 });
state = replication.logger.state().state;
assertFalse(state.running);
assertMatch(/^\d+$/, state.lastLogTick);
assertTrue(state.totalEvents >= 0);
assertEqual(tick, state.lastLogTick);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test logging enabled
////////////////////////////////////////////////////////////////////////////////
testEnabledLogger : function () {
var state, tick;
state = replication.logger.state().state;
assertFalse(state.running);
tick = state.lastLogTick;
assertTrue(typeof tick === 'string');
assertMatch(/^\d+$/, state.lastLogTick);
assertTrue(state.totalEvents >= 0);
replication.logger.start();
// do something that will cause logging
var c = db._create(cn);
c.save({ "test" : 1 });
state = replication.logger.state().state;
assertTrue(state.running);
assertMatch(/^\d+$/, state.lastLogTick);
assertTrue(state.totalEvents >= 3);
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test logging, total events
////////////////////////////////////////////////////////////////////////////////
testEventsLogger : function () {
var state;
replication.logger.start();
state = replication.logger.state().state;
assertTrue(state.totalEvents >= 1);
var value = state.totalEvents;
replication.logger.stop();
state = replication.logger.state().state;
assertEqual(value + 1, state.totalEvents);
assertTrue(state.totalEvents >= 0);
value = state.totalEvents;
replication.logger.start();
state = replication.logger.state().state;
assertEqual(value + 1, state.totalEvents);
value = state.totalEvents;
// do something that will cause logging
var c = db._create(cn);
state = replication.logger.state().state;
assertEqual(value + 1, state.totalEvents);
value = state.totalEvents;
c.save({ "test" : 1 });
state = replication.logger.state().state;
assertEqual(value + 1, state.totalEvents);
value = state.totalEvents;
replication.logger.stop();
state = replication.logger.state().state;
assertEqual(value + 1, state.totalEvents);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test logger properties
////////////////////////////////////////////////////////////////////////////////
testPropertiesLogger : function () {
var properties;
properties = replication.logger.properties();
assertTrue(typeof properties === 'object');
assertTrue(properties.hasOwnProperty('autoStart'));
assertTrue(properties.hasOwnProperty('logRemoteChanges'));
assertTrue(properties.hasOwnProperty('maxEvents'));
assertTrue(properties.hasOwnProperty('maxEventsSize'));
var autoStart = properties.autoStart;
var maxEvents = properties.maxEvents;
var maxEventsSize = properties.maxEventsSize;
assertFalse(properties.logRemoteChanges);
properties = replication.logger.properties({
logRemoteChanges: true
});
assertTrue(typeof properties === 'object');
assertTrue(properties.hasOwnProperty('autoStart'));
assertTrue(properties.hasOwnProperty('logRemoteChanges'));
assertTrue(properties.logRemoteChanges);
assertTrue(properties.hasOwnProperty('maxEvents'));
assertTrue(properties.hasOwnProperty('maxEventsSize'));
assertEqual(autoStart, properties.autoStart);
assertEqual(maxEvents, properties.maxEvents);
assertEqual(maxEventsSize, properties.maxEventsSize);
properties = replication.logger.properties({
logRemoteChanges: false
});
assertTrue(typeof properties === 'object');
assertTrue(properties.hasOwnProperty('autoStart'));
assertTrue(properties.hasOwnProperty('logRemoteChanges'));
assertTrue(properties.hasOwnProperty('maxEvents'));
assertTrue(properties.hasOwnProperty('maxEventsSize'));
assertEqual(autoStart, properties.autoStart);
assertFalse(properties.logRemoteChanges);
assertEqual(maxEvents, properties.maxEvents);
assertEqual(maxEventsSize, properties.maxEventsSize);
properties = replication.logger.properties({
autoStart: true
});
assertTrue(typeof properties === 'object');
assertTrue(properties.hasOwnProperty('autoStart'));
assertTrue(properties.hasOwnProperty('logRemoteChanges'));
assertTrue(properties.hasOwnProperty('maxEvents'));
assertTrue(properties.hasOwnProperty('maxEventsSize'));
assertEqual(true, properties.autoStart);
assertFalse(properties.logRemoteChanges);
assertEqual(maxEvents, properties.maxEvents);
assertEqual(maxEventsSize, properties.maxEventsSize);
properties = replication.logger.properties({
autoStart: false
});
assertTrue(typeof properties === 'object');
assertTrue(properties.hasOwnProperty('autoStart'));
assertTrue(properties.hasOwnProperty('logRemoteChanges'));
assertTrue(properties.hasOwnProperty('maxEvents'));
assertTrue(properties.hasOwnProperty('maxEventsSize'));
assertEqual(false, properties.autoStart);
assertFalse(properties.logRemoteChanges);
assertEqual(maxEvents, properties.maxEvents);
assertEqual(maxEventsSize, properties.maxEventsSize);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test event sizes
////////////////////////////////////////////////////////////////////////////////
testEventSizesLogger : function () {
var properties;
properties = replication.logger.properties();
assertTrue(typeof properties === 'object');
var maxEvents = properties.maxEvents;
var maxEventsSize = properties.maxEventsSize;
properties = replication.logger.properties({
maxEvents: 8192
});
assertTrue(typeof properties === 'object');
assertTrue(properties.hasOwnProperty('maxEvents'));
assertTrue(properties.hasOwnProperty('maxEventsSize'));
assertEqual(8192, properties.maxEvents);
assertEqual(maxEventsSize, properties.maxEventsSize);
properties = replication.logger.properties({
maxEventsSize: 16777216
});
assertTrue(typeof properties === 'object');
assertTrue(properties.hasOwnProperty('maxEvents'));
assertTrue(properties.hasOwnProperty('maxEventsSize'));
assertEqual(8192, properties.maxEvents);
assertEqual(16777216, properties.maxEventsSize);
properties = replication.logger.properties({
maxEvents: 16384,
maxEventsSize: 1048576
});
assertTrue(typeof properties === 'object');
assertTrue(properties.hasOwnProperty('maxEvents'));
assertTrue(properties.hasOwnProperty('maxEventsSize'));
assertEqual(16384, properties.maxEvents);
assertEqual(1048576, properties.maxEventsSize);
properties = replication.logger.properties({
maxEvents: 0,
maxEventsSize: 1048580
});
assertTrue(typeof properties === 'object');
assertTrue(properties.hasOwnProperty('maxEvents'));
assertTrue(properties.hasOwnProperty('maxEventsSize'));
assertEqual(0, properties.maxEvents);
assertEqual(1048580, properties.maxEventsSize);
properties = replication.logger.properties({
maxEvents: 16384,
maxEventsSize: 0
});
assertTrue(typeof properties === 'object');
assertTrue(properties.hasOwnProperty('maxEvents'));
assertTrue(properties.hasOwnProperty('maxEventsSize'));
assertEqual(16384, properties.maxEvents);
assertEqual(0, properties.maxEventsSize);
try {
properties = replication.logger.properties({
maxEvents: 10,
maxEventsSize: 0
});
fail();
}
catch (err1) {
assertEqual(errors.ERROR_REPLICATION_INVALID_LOGGER_CONFIGURATION.code, err1.errorNum);
}
try {
properties = replication.logger.properties({
maxEvents: 0,
maxEventsSize: 10
});
fail();
}
catch (err2) {
assertEqual(errors.ERROR_REPLICATION_INVALID_LOGGER_CONFIGURATION.code, err2.errorNum);
}
try {
properties = replication.logger.properties({
maxEvents: 10,
maxEventsSize: 10
});
fail();
}
catch (err3) {
assertEqual(errors.ERROR_REPLICATION_INVALID_LOGGER_CONFIGURATION.code, err3.errorNum);
}
try {
properties = replication.logger.properties({
maxEvents: 16384,
maxEventsSize: 10
});
fail();
}
catch (err4) {
assertEqual(errors.ERROR_REPLICATION_INVALID_LOGGER_CONFIGURATION.code, err4.errorNum);
}
try {
properties = replication.logger.properties({
maxEvents: 10,
maxEventsSize: 1048576
});
fail();
}
catch (err5) {
assertEqual(errors.ERROR_REPLICATION_INVALID_LOGGER_CONFIGURATION.code, err5.errorNum);
}
properties = replication.logger.properties({
maxEvents: 0,
maxEventsSize: 0
});
assertTrue(typeof properties === 'object');
assertTrue(properties.hasOwnProperty('maxEvents'));
assertTrue(properties.hasOwnProperty('maxEventsSize'));
assertEqual(0, properties.maxEvents);
assertEqual(0, properties.maxEventsSize);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test capped logging
////////////////////////////////////////////////////////////////////////////////
testCappedLogger : function () {
var state, tick;
state = replication.logger.state().state;
assertFalse(state.running);
tick = state.lastLogTick;
assertTrue(typeof tick === 'string');
replication.logger.properties({ maxEvents: 5000 });
replication.logger.start();
// do something that will cause logging
var c = db._create(cn);
for (var i = 0; i < 50000; ++i) {
c.save({ value: i });
}
assertEqual(5000, db._collection('_replication').count());
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test uncapped logging
////////////////////////////////////////////////////////////////////////////////
testUncappedLogger : function () {
var state, tick;
state = replication.logger.state().state;
assertFalse(state.running);
tick = state.lastLogTick;
assertTrue(typeof tick === 'string');
// manually flush all entries in the collection
db._collection('_replication').truncate();
replication.logger.properties({ maxEvents: 0, maxEventsSize: 0 });
replication.logger.start();
// do something that will cause logging
var c = db._create(cn);
for (var i = 0; i < 50000; ++i) {
c.save({ value: i });
}
// 50000 + transaction start + transaction commit
assertEqual(50000 + 2, db._collection('_replication').count());
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateCollection : function () {
var state, tick;
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
var c = db._create(cn);
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2000, entry.type);
entry = JSON.parse(entry.data);
assertEqual(2, entry.collection.type);
assertEqual(c._id, entry.cid);
assertEqual(c._id, entry.collection.cid);
assertEqual(cn, entry.cname);
assertFalse(entry.collection.deleted);
assertEqual(cn, entry.collection.name);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerDropCollection : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
db._drop(cn);
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2001, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerRenameCollection : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.rename(cn2);
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2002, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(cn2, entry.collection.name);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerPropertiesCollection1 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.properties();
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(0, compareTicks(state.lastLogTick, tick));
assertEqual(count, getLogEntries());
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerPropertiesCollection2 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.properties({ waitForSync: true, journalSize: 2097152 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2003, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(c._id, entry.collection.cid);
assertEqual(cn, entry.cname);
assertEqual(cn, entry.collection.name);
assertEqual(2, entry.collection.type);
assertEqual(false, entry.collection.deleted);
assertEqual(2097152, entry.collection.maximalSize);
assertEqual(true, entry.collection.waitForSync);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerIncludedSystemCollection : function () {
var state, tick;
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c = db._collection("_graphs");
var doc = c.save({ "test": 1 });
state = replication.logger.state().state;
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2300, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(c.name(), entry.cname);
c.remove(doc._key);
entry = getLastLogEntry();
assertEqual(2302, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(c.name(), entry.cname);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerSystemCollection : function () {
var state, tick, i;
db._drop("_unitfoxx");
db._drop("_unittests");
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
var c = db._create("_unittests", { isSystem : true });
state = replication.logger.state().state;
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2000, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(c.name(), entry.cname);
c.properties({ waitForSync : true });
state = replication.logger.state().state;
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 2, getLogEntries());
entry = getLastLogEntry();
assertEqual(2003, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(c.name(), entry.cname);
c.rename("_unitfoxx");
state = replication.logger.state().state;
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 3, getLogEntries());
entry = getLastLogEntry();
assertEqual(2002, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual("_unittests", entry.cname);
c.rename("_unittests");
state = replication.logger.state().state;
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 4, getLogEntries());
entry = getLastLogEntry();
assertEqual(2002, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual("_unitfoxx", entry.cname);
for (i = 0; i < 100; ++i) {
c.save({ "_key" : "test" + i });
}
state = replication.logger.state().state;
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 104, getLogEntries());
entry = getLastLogEntry();
assertEqual(2300, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual("_unittests", entry.cname);
for (i = 0; i < 50; ++i) {
c.remove("test" + i);
}
state = replication.logger.state().state;
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 154, getLogEntries());
entry = getLastLogEntry();
assertEqual(2302, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual("_unittests", entry.cname);
c.truncate();
state = replication.logger.state().state;
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 206, getLogEntries());
entry = getLastLogEntry();
assertEqual(2201, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.collections[0].cid);
assertEqual("_unittests", entry.collections[0].name);
db._drop("_unittests");
db._drop("_unitfoxx");
state = replication.logger.state().state;
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 207, getLogEntries());
entry = getLastLogEntry();
assertEqual(2001, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual("_unittests", entry.cname);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTruncateCollection1 : function () {
var state, tick;
var c = db._create(cn);
c.save({ "test": 1, "_key": "abc" });
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.truncate();
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 3, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
c.truncate();
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
c.save({ "test": 1, "_key": "abc" });
var rev = c.document("abc")._rev;
state = replication.logger.state().state;
tick = state.lastLogTick;
count = getLogEntries();
c.truncate();
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 3, getLogEntries());
var entries = getLastLogEntry(3), entry;
// trx start
entry = entries.pop();
assertEqual(2200, entry.type);
entry = JSON.parse(entry.data);
assertEqual(1, entry.collections.length);
assertEqual(c._id, entry.collections[0].cid);
assertEqual(cn, entry.collections[0].name);
assertEqual(1, entry.collections[0].operations);
assertTrue(entry.tid != "");
var tid = entry.tid;
// remove
entry = entries.pop();
assertEqual(2302, entry.type);
entry = JSON.parse(entry.data);
assertEqual("abc", entry.key);
assertEqual(rev, entry.oldRev);
assertEqual(tid, entry.tid);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
// commit
entry = entries.pop();
assertEqual(2201, entry.type);
entry = JSON.parse(entry.data);
assertEqual(1, entry.collections.length);
assertEqual(c._id, entry.collections[0].cid);
assertEqual(cn, entry.collections[0].name);
assertEqual(1, entry.collections[0].operations);
assertEqual(tid, entry.tid);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTruncateCollection2 : function () {
var state, tick;
var c = db._create(cn);
for (var i = 0; i < 100; ++i) {
c.save({ "test": 1, "_key": "test" + i });
}
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.truncate();
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 102, getLogEntries());
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexHash1 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureUniqueConstraint("a", "b");
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("hash", entry.index.type);
assertEqual(true, entry.index.unique);
assertEqual([ "a", "b" ], entry.index.fields);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexHash2 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureHashIndex("a");
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("hash", entry.index.type);
assertEqual(false, entry.index.unique);
assertEqual([ "a" ], entry.index.fields);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexSkiplist1 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureSkiplist("a", "b", "c");
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("skiplist", entry.index.type);
assertEqual(false, entry.index.unique);
assertEqual([ "a", "b", "c" ], entry.index.fields);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexSkiplist2 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureUniqueSkiplist("a");
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("skiplist", entry.index.type);
assertEqual(true, entry.index.unique);
assertEqual([ "a" ], entry.index.fields);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexFulltext1 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureFulltextIndex("a", 5);
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("fulltext", entry.index.type);
assertEqual(false, entry.index.unique);
assertEqual(5, entry.index.minLength);
assertEqual([ "a" ], entry.index.fields);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexGeo1 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureGeoIndex("a", "b");
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("geo2", entry.index.type);
assertEqual(false, entry.index.unique);
assertEqual(false, entry.index.constraint);
assertEqual([ "a", "b" ], entry.index.fields);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexGeo2 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureGeoIndex("a", true);
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("geo1", entry.index.type);
assertEqual(false, entry.index.unique);
assertEqual(false, entry.index.constraint);
assertEqual([ "a" ], entry.index.fields);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexGeo3 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureGeoConstraint("a", "b", true);
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("geo2", entry.index.type);
assertEqual(true, entry.index.unique);
assertEqual(true, entry.index.constraint);
assertEqual(true, entry.index.ignoreNull);
assertEqual([ "a", "b" ], entry.index.fields);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexGeo4 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureGeoConstraint("a", "b", false);
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("geo2", entry.index.type);
assertEqual(true, entry.index.unique);
assertEqual(true, entry.index.constraint);
assertEqual(false, entry.index.ignoreNull);
assertEqual([ "a", "b" ], entry.index.fields);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexGeo5 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureGeoConstraint("a", true);
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("geo1", entry.index.type);
assertEqual(true, entry.index.unique);
assertEqual(true, entry.index.constraint);
assertEqual([ "a" ], entry.index.fields);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexCap1 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureCapConstraint(100);
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("cap", entry.index.type);
assertEqual(false, entry.index.unique);
assertEqual(100, entry.index.size);
assertEqual(0, entry.index.byteSize);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerCreateIndexCap2 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.ensureCapConstraint(null, 1048576);
var idx = c.getIndexes()[1];
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2100, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.index.id);
assertEqual("cap", entry.index.type);
assertEqual(false, entry.index.unique);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerDropIndex : function () {
var state, tick;
var c = db._create(cn);
c.ensureUniqueConstraint("a", "b");
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
// use index at #1 (#0 is primary index)
var idx = c.getIndexes()[1];
c.dropIndex(idx);
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertTrue(2101, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual(idx.id.replace(/^.*\//, ''), entry.id);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerSaveDocument : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.save({ "test": 1, "_key": "abc" });
var rev = c.document("abc")._rev;
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2300, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("abc", entry.key);
assertEqual("abc", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(1, entry.data.test);
tick = state.lastLogTick;
count = getLogEntries();
c.save({ "test": 2, "foo" : "bar", "_key": "12345" });
rev = c.document("12345")._rev;
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
entry = getLastLogEntry();
assertEqual(2300, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("12345", entry.key);
assertEqual("12345", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(2, entry.data.test);
assertEqual("bar", entry.data.foo);
tick = state.lastLogTick;
count = getLogEntries();
try {
c.save({ "test": 1, "_key": "12345" });
fail();
}
catch (err) {
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerSaveDocuments : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
for (var i = 0; i < 100; ++i) {
c.save({ "test": 1, "_key": "test" + i });
}
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 100, getLogEntries());
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerDeleteDocument : function () {
var state, tick;
var c = db._create(cn);
c.save({ "test": 1, "_key": "abc" });
c.save({ "test": 1, "_key": "12345" });
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
var rev = c.document("abc")._rev;
c.remove("abc");
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2302, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("abc", entry.key);
assertEqual(rev, entry.oldRev);
tick = state.lastLogTick;
count = getLogEntries();
rev = c.document("12345")._rev;
c.remove("12345");
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
entry = getLastLogEntry();
assertEqual(2302, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("12345", entry.key);
assertEqual(rev, entry.oldRev);
tick = state.lastLogTick;
count = getLogEntries();
try {
c.remove("12345");
fail();
}
catch (err) {
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerUpdateDocument : function () {
var state, tick;
var c = db._create(cn);
c.save({ "test": 1, "_key": "abc" });
c.save({ "test": 1, "_key": "12345" });
var oldRev = c.document("abc")._rev;
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.update("abc", { "test" : 2 });
var rev = c.document("abc")._rev;
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2300, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("abc", entry.key);
assertEqual(oldRev, entry.oldRev);
assertEqual("abc", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(2, entry.data.test);
tick = state.lastLogTick;
count = getLogEntries();
oldRev = rev;
c.update("abc", { "test" : 3 });
rev = c.document("abc")._rev;
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
entry = getLastLogEntry();
assertEqual(2300, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("abc", entry.key);
assertEqual(oldRev, entry.oldRev);
assertEqual("abc", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(3, entry.data.test);
tick = state.lastLogTick;
count = getLogEntries();
c.update("abc", { "test" : 3 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
c.update("12345", { "test" : 2 });
c.update("abc", { "test" : 4 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 2, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
try {
c.update("thefoxx", { });
fail();
}
catch (err) {
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerReplaceDocument : function () {
var state, tick;
var c = db._create(cn);
c.save({ "test": 1, "_key": "abc" });
c.save({ "test": 1, "_key": "12345" });
var oldRev = c.document("abc")._rev;
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
c.replace("abc", { "test" : 2 });
var rev = c.document("abc")._rev;
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2300, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("abc", entry.key);
assertEqual(oldRev, entry.oldRev);
assertEqual("abc", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(2, entry.data.test);
tick = state.lastLogTick;
count = getLogEntries();
c.replace("abc", { "test" : 3 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
c.replace("abc", { "test" : 3 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
c.replace("12345", { "test" : 2 });
c.replace("abc", { "test" : 4 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 2, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
try {
c.replace("thefoxx", { });
fail();
}
catch (err) {
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerSaveEdge : function () {
var state, tick;
db._create(cn);
var e = db._createEdgeCollection(cn2);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
e.save(cn + "/test1", cn + "/test2", { "test": 1, "_key": "abc" });
var rev = e.document("abc")._rev;
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2301, entry.type);
entry = JSON.parse(entry.data);
assertEqual(e._id, entry.cid);
assertEqual(cn2, entry.cname);
assertEqual("abc", entry.key);
assertEqual("abc", entry.data._key);
assertEqual(cn + "/test1", entry.data._from);
assertEqual(cn + "/test2", entry.data._to);
assertEqual(rev, entry.data._rev);
assertEqual(1, entry.data.test);
tick = state.lastLogTick;
count = getLogEntries();
e.save(cn + "/test3", cn + "/test4", { "test": [ 99, false ], "_key": "12345" });
rev = e.document("12345")._rev;
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
entry = getLastLogEntry();
assertEqual(2301, entry.type);
entry = JSON.parse(entry.data);
assertEqual(e._id, entry.cid);
assertEqual(cn2, entry.cname);
assertEqual("12345", entry.key);
assertEqual("12345", entry.data._key);
assertEqual(cn + "/test3", entry.data._from);
assertEqual(cn + "/test4", entry.data._to);
assertEqual(rev, entry.data._rev);
assertEqual([ 99, false ], entry.data.test);
tick = state.lastLogTick;
count = getLogEntries();
try {
e.save();
fail();
}
catch (err) {
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerDeleteEdge : function () {
var state, tick;
db._create(cn);
var e = db._createEdgeCollection(cn2);
e.save(cn + "/test1", cn + "/test2", { "test": 1, "_key": "abc" });
e.save(cn + "/test3", cn + "/test4", { "test": 1, "_key": "12345" });
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
var rev = e.document("abc")._rev;
e.remove("abc");
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2302, entry.type);
entry = JSON.parse(entry.data);
assertEqual(e._id, entry.cid);
assertEqual(cn2, entry.cname);
assertEqual("abc", entry.key);
assertEqual(rev, entry.oldRev);
tick = state.lastLogTick;
count = getLogEntries();
e.remove("12345");
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
try {
e.remove("12345");
fail();
}
catch (err) {
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerUpdateEdge : function () {
var state, tick;
db._create(cn);
var e = db._createEdgeCollection(cn2);
e.save(cn + "/test1", cn + "/test2", { "test": 1, "_key": "abc" });
e.save(cn + "/test3", cn + "/test4", { "test": 1, "_key": "12345" });
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
e.update("abc", { "test" : 2 });
var rev = e.document("abc")._rev;
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2301, entry.type);
entry = JSON.parse(entry.data);
assertEqual(e._id, entry.cid);
assertEqual(cn2, entry.cname);
assertEqual("abc", entry.key);
assertEqual("abc", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(2, entry.data.test);
tick = state.lastLogTick;
count = getLogEntries();
e.update("abc", { "test" : 3 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
e.update("abc", { "test" : 3 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
e.update("12345", { "test" : 2 });
e.update("abc", { "test" : 4 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 2, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
try {
e.update("thefoxx", { });
fail();
}
catch (err) {
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerReplaceEdge : function () {
var state, tick;
db._create(cn);
var e = db._createEdgeCollection(cn2);
e.save(cn + "/test1", cn + "/test2", { "test": 1, "_key": "abc" });
e.save(cn + "/test3", cn + "/test4", { "test": 1, "_key": "12345" });
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
e.replace("abc", { "test" : 2 });
var rev = e.document("abc")._rev;
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
var entry = getLastLogEntry();
assertEqual(2301, entry.type);
entry = JSON.parse(entry.data);
assertEqual(e._id, entry.cid);
assertEqual(cn2, entry.cname);
assertEqual("abc", entry.key);
assertEqual("abc", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(2, entry.data.test);
tick = state.lastLogTick;
count = getLogEntries();
e.replace("abc", { "test" : 3 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
e.replace("abc", { "test" : 3 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 1, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
e.replace("12345", { "test" : 2 });
e.replace("abc", { "test" : 4 });
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 2, getLogEntries());
tick = state.lastLogTick;
count = getLogEntries();
try {
e.replace("thefoxx", { });
fail();
}
catch (err) {
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionEmpty : function () {
var state, tick;
c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
var actual = db._executeTransaction({
collections: {
},
action: function () {
return true;
}
});
assertTrue(actual);
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionRead1 : function () {
var state, tick;
var c = db._create(cn);
c.save({ "test" : 1 });
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
var actual = db._executeTransaction({
collections: {
read: cn
},
action: function () {
return true;
}
});
assertTrue(actual);
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionRead2 : function () {
var state, tick;
var c = db._create(cn);
c.save({ "test" : 1, "_key": "abc" });
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
var actual = db._executeTransaction({
collections: {
read: cn
},
action: function (params) {
var c = require("internal").db._collection(params.cn);
c.document("abc");
return true;
},
params: {
cn: cn
}
});
assertTrue(actual);
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionRead3 : function () {
var state, tick;
db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
try {
actual = db._executeTransaction({
collections: {
read: cn
},
action: function (params) {
var c = require("internal").db._collection(params.cn);
c.save({ "foo" : "bar" });
return true;
},
params: {
cn: cn
}
});
fail();
}
catch (err) {
}
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionWrite1 : function () {
var state, tick;
db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
var actual = db._executeTransaction({
collections: {
write: cn
},
action: function () {
return true;
}
});
assertTrue(actual);
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionWrite2 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
var actual = db._executeTransaction({
collections: {
write: cn
},
action: function (params) {
var c = require("internal").db._collection(params.cn);
c.save({ "test" : 2, "_key": "abc" });
return true;
},
params: {
cn: cn
}
});
assertTrue(actual);
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 3, getLogEntries());
var rev = c.document("abc")._rev;
var entries = getLastLogEntry(3), entry;
entry = entries.pop();
assertEqual(2200, entry.type);
assertTrue(entry.tid != "");
var tid = entry.tid;
entry = JSON.parse(entry.data);
assertEqual(1, entry.collections.length);
assertEqual(c._id, entry.collections[0].cid);
assertEqual(cn, entry.collections[0].name);
assertEqual(1, entry.collections[0].operations);
entry = entries.pop();
assertEqual(2300, entry.type);
assertEqual(tid, entry.tid);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("abc", entry.key);
assertEqual("abc", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(2, entry.data.test);
entry = entries.pop();
assertEqual(2201, entry.type);
assertEqual(tid, entry.tid);
entry = JSON.parse(entry.data);
assertEqual(1, entry.collections.length);
assertEqual(c._id, entry.collections[0].cid);
assertEqual(cn, entry.collections[0].name);
assertEqual(1, entry.collections[0].operations);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionWrite3 : function () {
var state, tick;
db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
try {
db._executeTransaction({
collections: {
write: cn
},
action: function (params) {
var c = require("internal").db._collection(params.cn);
c.save({ "test" : 2, "_key": "abc" });
throw "fail";
},
params: {
cn: cn
}
});
fail();
}
catch (err) {
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionWrite4 : function () {
var state, tick;
db._create(cn);
db._create(cn2);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
try {
db._executeTransaction({
collections: {
write: cn
},
action: function (params) {
var c2 = require("internal").db._collection(params.cn2);
c2.save({ "test" : 2, "_key": "abc" });
},
params: {
cn2: cn2
}
});
fail();
}
catch (err) {
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionWrite5 : function () {
var state, tick;
var c1 = db._create(cn);
db._create(cn2);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
db._executeTransaction({
collections: {
write: [ cn, cn2 ]
},
action: function (params) {
var c1 = require("internal").db._collection(params.cn);
c1.save({ "test" : 1, "_key": "12345" });
c1.save({ "test" : 2, "_key": "abc" });
},
params: {
cn: cn
}
});
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 4, getLogEntries());
var entries = getLastLogEntry(4), entry;
entry = entries.pop();
assertEqual(2200, entry.type);
assertTrue(entry.tid != "");
var tid = entry.tid;
entry = JSON.parse(entry.data);
assertEqual(1, entry.collections.length);
assertEqual(c1._id, entry.collections[0].cid);
assertEqual(cn, entry.collections[0].name);
assertEqual(2, entry.collections[0].operations);
var rev = c1.document("12345")._rev;
entry = entries.pop();
assertEqual(2300, entry.type);
assertEqual(tid, entry.tid);
entry = JSON.parse(entry.data);
assertEqual(c1._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("12345", entry.key);
assertEqual("12345", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(1, entry.data.test);
rev = c1.document("abc")._rev;
entry = entries.pop();
assertEqual(2300, entry.type);
assertEqual(tid, entry.tid);
entry = JSON.parse(entry.data);
assertEqual(c1._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("abc", entry.key);
assertEqual("abc", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(2, entry.data.test);
entry = entries.pop();
assertEqual(2201, entry.type);
assertEqual(tid, entry.tid);
entry = JSON.parse(entry.data);
assertEqual(1, entry.collections.length);
assertEqual(c1._id, entry.collections[0].cid);
assertEqual(cn, entry.collections[0].name);
assertEqual(2, entry.collections[0].operations);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test actions
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionWrite6 : function () {
var state, tick;
var c1 = db._create(cn);
var c2 = db._create(cn2);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
db._executeTransaction({
collections: {
write: [ cn, cn2 ]
},
action: function (params) {
var c1 = require("internal").db._collection(params.cn);
var c2 = require("internal").db._collection(params.cn2);
c1.save({ "test" : 1, "_key": "12345" });
c2.save({ "test" : 2, "_key": "abc" });
},
params: {
cn: cn,
cn2: cn2
}
});
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 4, getLogEntries());
var entries = getLastLogEntry(4), entry;
entry = entries.pop();
assertEqual(2200, entry.type);
assertTrue(entry.tid != "");
var tid = entry.tid;
entry = JSON.parse(entry.data);
assertEqual(2, entry.collections.length);
assertEqual(c1._id, entry.collections[0].cid);
assertEqual(cn, entry.collections[0].name);
assertEqual(1, entry.collections[0].operations);
assertEqual(c2._id, entry.collections[1].cid);
assertEqual(cn2, entry.collections[1].name);
assertEqual(1, entry.collections[1].operations);
var rev = c1.document("12345")._rev;
entry = entries.pop();
assertEqual(2300, entry.type);
assertEqual(tid, entry.tid);
entry = JSON.parse(entry.data);
assertEqual(c1._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("12345", entry.key);
assertEqual("12345", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(1, entry.data.test);
rev = c2.document("abc")._rev;
entry = entries.pop();
assertEqual(2300, entry.type);
assertEqual(tid, entry.tid);
entry = JSON.parse(entry.data);
assertEqual(c2._id, entry.cid);
assertEqual(cn2, entry.cname);
assertEqual("abc", entry.key);
assertEqual("abc", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(2, entry.data.test);
entry = entries.pop();
assertEqual(2201, entry.type);
assertEqual(tid, entry.tid);
entry = JSON.parse(entry.data);
assertEqual(2, entry.collections.length);
assertEqual(c1._id, entry.collections[0].cid);
assertEqual(cn, entry.collections[0].name);
assertEqual(1, entry.collections[0].operations);
assertEqual(c2._id, entry.collections[1].cid);
assertEqual(cn2, entry.collections[1].name);
assertEqual(1, entry.collections[1].operations);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test collection exclusion
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionExcluded1 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
db._executeTransaction({
collections: {
write: [ cn, "_users" ]
},
action: function (params) {
var c = require("internal").db._collection(params.cn);
var users = require("internal").db._collection("_users");
c.save({ "test" : 2, "_key": "12345" });
users.save({ "_key": "unittests1", "foo": false });
users.remove("unittests1");
},
params: {
cn: cn
}
});
state = replication.logger.state().state;
assertNotEqual(tick, state.lastLogTick);
assertEqual(1, compareTicks(state.lastLogTick, tick));
assertEqual(count + 3, getLogEntries());
var entries = getLastLogEntry(3), entry;
entry = entries.pop();
assertEqual(2200, entry.type);
assertTrue(entry.tid != "");
var tid = entry.tid;
entry = JSON.parse(entry.data);
assertEqual(1, entry.collections.length);
assertEqual(c._id, entry.collections[0].cid);
assertEqual(cn, entry.collections[0].name);
assertEqual(1, entry.collections[0].operations);
var rev = c.document("12345")._rev;
entry = entries.pop();
assertEqual(2300, entry.type);
assertEqual(tid, entry.tid);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("12345", entry.key);
assertEqual("12345", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(2, entry.data.test);
entry = entries.pop();
assertEqual(2201, entry.type);
assertEqual(tid, entry.tid);
entry = JSON.parse(entry.data);
assertEqual(1, entry.collections.length);
assertEqual(c._id, entry.collections[0].cid);
assertEqual(cn, entry.collections[0].name);
assertEqual(1, entry.collections[0].operations);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test collection exclusion
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionExcluded2 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
c.save({ "test" : 1, "_key": "12345" });
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
db._executeTransaction({
collections: {
write: [ cn ]
},
action: function (params) {
var c = require("internal").db._collection(params.cn);
c.save({ "test" : 1, "_key" : "abc" });
},
params: {
cn: cn
},
replicate: false
});
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
var entry = getLastLogEntry();
var rev = c.document("12345")._rev;
assertEqual(2300, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("12345", entry.key);
assertEqual("12345", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(1, entry.data.test);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test collection exclusion
////////////////////////////////////////////////////////////////////////////////
testLoggerTransactionExcluded3 : function () {
var state, tick;
var c = db._create(cn);
replication.logger.start();
c.save({ "test" : 1, "_key": "12345" });
state = replication.logger.state().state;
tick = state.lastLogTick;
var count = getLogEntries();
db._executeTransaction({
collections: {
write: [ cn ]
},
action: function (params) {
var c = require("internal").db._collection(params.cn), i;
for (i = 0; i < 100; ++i) {
c.save({ "test" : 1, "_key" : "abc" + i });
}
for (i = 0; i < 100; ++i) {
c.remove("abc" + i);
}
},
params: {
cn: cn
},
replicate: false
});
state = replication.logger.state().state;
assertEqual(tick, state.lastLogTick);
assertEqual(count, getLogEntries());
var entry = getLastLogEntry();
var rev = c.document("12345")._rev;
assertEqual(2300, entry.type);
entry = JSON.parse(entry.data);
assertEqual(c._id, entry.cid);
assertEqual(cn, entry.cname);
assertEqual("12345", entry.key);
assertEqual("12345", entry.data._key);
assertEqual(rev, entry.data._rev);
assertEqual(1, entry.data.test);
}
};
}
// -----------------------------------------------------------------------------
// --SECTION-- replication applier test
// -----------------------------------------------------------------------------
////////////////////////////////////////////////////////////////////////////////
/// @brief test suite
////////////////////////////////////////////////////////////////////////////////
function ReplicationApplierSuite () {
return {
////////////////////////////////////////////////////////////////////////////////
/// @brief set up
////////////////////////////////////////////////////////////////////////////////
setUp : function () {
replication.applier.stop();
replication.applier.forget();
},
////////////////////////////////////////////////////////////////////////////////
/// @brief tear down
////////////////////////////////////////////////////////////////////////////////
tearDown : function () {
replication.applier.stop();
},
////////////////////////////////////////////////////////////////////////////////
/// @brief start applier w/o configuration
////////////////////////////////////////////////////////////////////////////////
testStartApplierNoConfig : function () {
var state;
state = replication.applier.state();
assertFalse(state.state.running);
try {
// start
replication.applier.start();
fail();
}
catch (err) {
assertEqual(errors.ERROR_REPLICATION_INVALID_APPLIER_CONFIGURATION.code, err.errorNum);
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief start applier with configuration
////////////////////////////////////////////////////////////////////////////////
testStartApplierInvalidEndpoint1 : function () {
var state;
state = replication.applier.state();
assertFalse(state.state.running);
// configure && start
replication.applier.properties({
endpoint: "tcp://9.9.9.9:9999", // should not exist
connectTimeout: 3,
maxConnectRetries: 1
});
replication.applier.start();
state = replication.applier.state();
assertEqual(errors.ERROR_NO_ERROR.code, state.state.lastError.errorNum);
assertTrue(state.state.running);
var i = 0, max = 30;
while (i++ < max) {
internal.wait(1);
state = replication.applier.state();
if (state.state.running) {
continue;
}
assertFalse(state.state.running);
assertTrue(state.state.totalFailedConnects > 0);
assertTrue(state.state.progress.failedConnects > 0);
assertTrue(errors.ERROR_REPLICATION_NO_RESPONSE.code, state.state.lastError.errorNum);
break;
}
if (i >= max) {
fail();
}
// call start again
replication.applier.start();
state = replication.applier.state();
assertTrue(state.state.running);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief start applier with configuration
////////////////////////////////////////////////////////////////////////////////
testStartApplierInvalidEndpoint2 : function () {
var state;
state = replication.applier.state();
assertFalse(state.state.running);
// configure && start
replication.applier.properties({
endpoint: "tcp://www.arangodb.org:7999", // should not exist
connectTimeout: 3,
maxConnectRetries: 1
});
replication.applier.start();
state = replication.applier.state();
assertTrue(state.state.running);
var i = 0, max = 30;
while (i++ < max) {
internal.wait(1);
state = replication.applier.state();
if (state.state.running) {
continue;
}
assertFalse(state.state.running);
assertTrue(state.state.totalFailedConnects > 0);
assertTrue(state.state.progress.failedConnects > 0);
assertTrue(state.state.lastError.errorNum === errors.ERROR_REPLICATION_INVALID_RESPONSE.code ||
state.state.lastError.errorNum === errors.ERROR_REPLICATION_MASTER_ERROR.code ||
state.state.lastError.errorNum === errors.ERROR_REPLICATION_NO_RESPONSE.code);
break;
}
if (i >= max) {
fail();
}
// call start again
replication.applier.start();
state = replication.applier.state();
assertTrue(state.state.running);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief stop applier
////////////////////////////////////////////////////////////////////////////////
testStopApplier : function () {
var state;
state = replication.applier.state();
assertFalse(state.state.running);
// configure && start
replication.applier.properties({
endpoint: "tcp://9.9.9.9:9999" // should not exist
});
replication.applier.start();
state = replication.applier.state();
assertEqual(errors.ERROR_NO_ERROR.code, state.state.lastError.errorNum);
assertTrue(state.state.running);
// stop
replication.applier.stop();
state = replication.applier.state();
assertFalse(state.state.running);
// stop again
replication.applier.stop();
state = replication.applier.state();
assertFalse(state.state.running);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief properties
////////////////////////////////////////////////////////////////////////////////
testApplierProperties : function () {
var properties;
properties = replication.applier.properties();
assertEqual(300, properties.requestTimeout);
assertEqual(10, properties.connectTimeout);
assertEqual(100, properties.maxConnectRetries);
assertEqual(0, properties.chunkSize);
assertFalse(properties.autoStart);
assertTrue(properties.adaptivePolling);
assertUndefined(properties.endpoint);
try {
replication.applier.properties({ });
fail();
}
catch (err) {
assertEqual(errors.ERROR_REPLICATION_INVALID_APPLIER_CONFIGURATION.code, err.errorNum);
}
replication.applier.properties({
endpoint: "tcp://9.9.9.9:9999"
});
properties = replication.applier.properties();
assertEqual(properties.endpoint, "tcp://9.9.9.9:9999");
assertEqual(300, properties.requestTimeout);
assertEqual(10, properties.connectTimeout);
assertEqual(100, properties.maxConnectRetries);
assertEqual(0, properties.chunkSize);
assertFalse(properties.autoStart);
assertTrue(properties.adaptivePolling);
replication.applier.properties({
endpoint: "tcp://9.9.9.9:9998",
autoStart: true,
adaptivePolling: false,
requestTimeout: 5,
connectTimeout: 9,
maxConnectRetries: 4,
chunkSize: 65536
});
properties = replication.applier.properties();
assertEqual(properties.endpoint, "tcp://9.9.9.9:9998");
assertEqual(5, properties.requestTimeout);
assertEqual(9, properties.connectTimeout);
assertEqual(4, properties.maxConnectRetries);
assertEqual(65536, properties.chunkSize);
assertTrue(properties.autoStart);
assertFalse(properties.adaptivePolling);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief start property change while running
////////////////////////////////////////////////////////////////////////////////
testApplierPropertiesChange : function () {
var state;
replication.applier.properties({ endpoint: "tcp://9.9.9.9:9999" });
replication.applier.start();
state = replication.applier.state();
assertTrue(state.state.running);
try {
replication.applier.properties({ endpoint: "tcp://9.9.9.9:9998" });
fail();
}
catch (err) {
assertEqual(errors.ERROR_REPLICATION_RUNNING.code, err.errorNum);
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief applier state
////////////////////////////////////////////////////////////////////////////////
testStateApplier : function () {
var state;
state = replication.applier.state();
assertFalse(state.state.running);
assertMatch(/^\d+-\d+-\d+T\d+:\d+:\d+Z$/, state.state.time);
assertEqual(state.server.version, db._version());
assertNotEqual("", state.server.serverId);
assertMatch(/^\d+$/, state.server.serverId);
assertUndefined(state.endpoint);
}
};
}
// -----------------------------------------------------------------------------
// --SECTION-- sync
// -----------------------------------------------------------------------------
////////////////////////////////////////////////////////////////////////////////
/// @brief test suite
////////////////////////////////////////////////////////////////////////////////
function ReplicationSyncSuite () {
return {
////////////////////////////////////////////////////////////////////////////////
/// @brief set up
////////////////////////////////////////////////////////////////////////////////
setUp : function () {
replication.applier.stop();
replication.applier.forget();
replication.logger.stop();
},
////////////////////////////////////////////////////////////////////////////////
/// @brief tear down
////////////////////////////////////////////////////////////////////////////////
tearDown : function () {
},
////////////////////////////////////////////////////////////////////////////////
/// @brief server id
////////////////////////////////////////////////////////////////////////////////
testServerId : function () {
var result = replication.serverId();
assertTrue(typeof result === 'string');
assertMatch(/^\d+$/, result);
},
////////////////////////////////////////////////////////////////////////////////
/// @brief no endpoint
////////////////////////////////////////////////////////////////////////////////
testSyncNoEndpoint : function () {
try {
replication.sync();
fail();
}
catch (err) {
assertEqual(errors.ERROR_BAD_PARAMETER.code, err.errorNum);
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief invalid endpoint
////////////////////////////////////////////////////////////////////////////////
testSyncNoEndpoint : function () {
try {
replication.sync({
endpoint: "tcp://9.9.9.9:9999"
});
fail();
}
catch (err) {
assertEqual(errors.ERROR_REPLICATION_NO_RESPONSE.code, err.errorNum);
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief invalid response
////////////////////////////////////////////////////////////////////////////////
testSyncInvalidResponse : function () {
try {
replication.sync({
endpoint: "tcp://www.arangodb.org:80"
});
fail();
}
catch (err) {
assertTrue(err.errorNum === errors.ERROR_REPLICATION_INVALID_RESPONSE.code ||
err.errorNum === errors.ERROR_REPLICATION_MASTER_ERROR.code);
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief invalid restrictType
////////////////////////////////////////////////////////////////////////////////
testSyncRestrict1 : function () {
try {
replication.sync({
endpoint: "tcp://9.9.9.9:9999",
restrictType: "foo"
});
fail();
}
catch (err) {
assertTrue(errors.ERROR_BAD_PARAMETER.code === err.errorNum ||
errors.ERROR_HTTP_BAD_PARAMETER.code === err.errorNum);
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief invalid restrictCollections
////////////////////////////////////////////////////////////////////////////////
testSyncRestrict2 : function () {
try {
replication.sync({
endpoint: "tcp://9.9.9.9:9999",
restrictType: "exclude"
});
fail();
}
catch (err) {
assertTrue(errors.ERROR_BAD_PARAMETER.code === err.errorNum ||
errors.ERROR_HTTP_BAD_PARAMETER.code === err.errorNum);
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief invalid restrictCollections
////////////////////////////////////////////////////////////////////////////////
testSyncRestrict3 : function () {
try {
replication.sync({
endpoint: "tcp://9.9.9.9:9999",
restrictType: "include"
});
fail();
}
catch (err) {
assertTrue(errors.ERROR_BAD_PARAMETER.code === err.errorNum ||
errors.ERROR_HTTP_BAD_PARAMETER.code === err.errorNum);
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief invalid restrictCollections
////////////////////////////////////////////////////////////////////////////////
testSyncRestrict4 : function () {
try {
replication.sync({
endpoint: "tcp://9.9.9.9:9999",
restrictCollections: [ "foo" ]
});
fail();
}
catch (err) {
assertTrue(errors.ERROR_BAD_PARAMETER.code === err.errorNum ||
errors.ERROR_HTTP_BAD_PARAMETER.code === err.errorNum);
}
},
////////////////////////////////////////////////////////////////////////////////
/// @brief invalid restrictCollections
////////////////////////////////////////////////////////////////////////////////
testSyncRestrict5 : function () {
try {
replication.sync({
endpoint: "tcp://9.9.9.9:9999",
restrictType: "include",
restrictCollections: "foo"
});
fail();
}
catch (err) {
assertTrue(errors.ERROR_BAD_PARAMETER.code === err.errorNum ||
errors.ERROR_HTTP_BAD_PARAMETER.code === err.errorNum);
}
}
};
}
// -----------------------------------------------------------------------------
// --SECTION-- main
// -----------------------------------------------------------------------------
////////////////////////////////////////////////////////////////////////////////
/// @brief executes the test suites
////////////////////////////////////////////////////////////////////////////////
jsunity.run(ReplicationLoggerSuite);
jsunity.run(ReplicationApplierSuite);
jsunity.run(ReplicationSyncSuite);
return jsunity.done();
// Local Variables:
// mode: outline-minor
// outline-regexp: "^\\(/// @brief\\|/// @addtogroup\\|// --SECTION--\\|/// @page\\|/// @}\\)"
// End: