1
0
Fork 0
arangodb/tests/js/server/ddl/database-failures-creation.js

197 lines
5.4 KiB
JavaScript

/*jshint globalstrict:false, strict:false, maxlen: 400 */
/*global fail, assertEqual, AQL_EXECUTE, instanceInfo */
////////////////////////////////////////////////////////////////////////////////
/// @brief test failure scenarios
///
/// @file
///
/// DISCLAIMER
///
/// Copyright 2010-2019 ArangoDB 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 ArangoDB GmbH, Cologne, Germany
///
/// @author Heiko Kernbach
/// @author Copyright 2019, ArangoDB GmbH, Cologne, Germany
////////////////////////////////////////////////////////////////////////////////
var jsunity = require("jsunity");
var arangodb = require("@arangodb");
var db = arangodb.db;
var internal = require("internal");
const request = require('@arangodb/request');
const expect = require('chai').expect;
const wait = internal.wait;
let coordinator = instanceInfo.arangods.filter(arangod => {
return arangod.role === 'coordinator';
})[0];
const expectedSystemCollections = [
"_analyzers",
"_appbundles",
"_apps",
"_aqlfunctions",
"_fishbowl",
"_graphs",
"_jobs",
"_queues"
];
////////////////////////////////////////////////////////////////////////////////
/// @brief async helper
////////////////////////////////////////////////////////////////////////////////
const waitForJob = function (postJobRes) {
expect(postJobRes).to.have.property("status", 202);
expect(postJobRes).to.have.property("headers");
expect(postJobRes.headers).to.have.property('x-arango-async-id');
const jobId = postJobRes.headers['x-arango-async-id'];
expect(jobId).to.be.a('string');
const waitInterval = 1.0;
const maxWaitTime = 300;
const start = Date.now();
let jobFinished = false;
let timeoutExceeded = false;
let putJobRes;
while (!jobFinished && !timeoutExceeded) {
const duration = (Date.now() - start) / 1000;
timeoutExceeded = duration > maxWaitTime;
putJobRes = request.put(coordinator.url + `/_api/job/${jobId}`);
expect(putJobRes).to.have.property("status");
if (putJobRes.status === 204) {
wait(waitInterval);
} else {
jobFinished = true;
}
}
if (jobFinished) {
return putJobRes;
}
console.error(`Waiting for REST job timed out`);
return undefined;
};
////////////////////////////////////////////////////////////////////////////////
/// @brief test suite
////////////////////////////////////////////////////////////////////////////////
function databaseFailureSuite() {
'use strict';
var dn = "FailureDatabase";
var d;
return {
setUp: function () {
internal.debugClearFailAt();
try {
db._dropDatabase(dn);
} catch (ignore) {
}
/*
d = db._createDatabase(dn);
*/
},
tearDown: function () {
d = null;
internal.debugClearFailAt();
},
////////////////////////////////////////////////////////////////////////////////
/// @brief test database upgrade procedure, if some system collections are
/// already existing
////////////////////////////////////////////////////////////////////////////////
testHideDatabaseUntilCreationIsFinished: function () {
expectedSystemCollections.sort();
// this will trigger an internal sleep of 5 seconds during db creation
internal.debugSetFailAt("UpgradeTasks::HideDatabaseUntilCreationIsFinished");
// create the db async, with job API
const postJobRes = request.post(
coordinator.url + '/_api/database',
{
headers: {"x-arango-async": "store"},
body: {"name": dn}
}
);
// this should fail now
try {
db._useDatabase(dn);
fail();
} catch (err) {
}
// wait until database creation is finished
const jobRes = waitForJob(postJobRes);
// this should not fail anymore, db must be available now
db._useDatabase(dn);
let availableCollections = [];
db._collections().forEach(function (collection) {
availableCollections.push(collection.name());
});
availableCollections.sort();
assertEqual(expectedSystemCollections, availableCollections);
},
testDatabaseSomeExisting: function () {
expectedSystemCollections.sort();
internal.debugSetFailAt("UpgradeTasks::CreateCollectionsExistsGraphAqlFunctions");
d = db._createDatabase(dn);
db._useDatabase(dn);
let availableCollections = [];
db._collections().forEach(function (collection) {
availableCollections.push(collection.name());
});
availableCollections.sort();
assertEqual(expectedSystemCollections, availableCollections);
},
};
}
////////////////////////////////////////////////////////////////////////////////
/// @brief executes the test suites
////////////////////////////////////////////////////////////////////////////////
if (internal.debugCanUseFailAt()) {
jsunity.run(databaseFailureSuite);
}
return jsunity.done();