diff --git a/lib/db/mysql_wrapper.js b/lib/db/mysql_wrapper.js index 91c4634827d590ed31bc007ad03decbd4fcbec8b..45edfd7de9411ad1fbb41618544d635cb62ee1f1 100644 --- a/lib/db/mysql_wrapper.js +++ b/lib/db/mysql_wrapper.js @@ -40,7 +40,13 @@ exports.createClient = function(options) { }); }, ping: function(cb) { - this.realClient.ping(cb); + if (stalled) { + process.nextTick(function() { + cb("database is intentionally stalled"); + }); + } else { + this.realClient.ping(cb); + } }, _runNextQuery: function() { var self = this; diff --git a/lib/wsapi.js b/lib/wsapi.js index e23a50ce9872722011262ece41da40e4e4cccbf0..7ee1f4a8d24e85b058a316fb657d2e3585831c6a 100644 --- a/lib/wsapi.js +++ b/lib/wsapi.js @@ -251,8 +251,10 @@ exports.setup = function(options, app) { try { var api = require(path.join(__dirname, 'wsapi', f)); - // don't register read apis if we are configured as a writer - if (options.only_write_apis && !api.writes_db) return; + // don't register read apis if we are configured as a writer, + // with the exception of ping which tests database connection health. + if (options.only_write_apis && !api.writes_db && + operation != 'ping') return; wsapis[operation] = api; diff --git a/lib/wsapi/ping.js b/lib/wsapi/ping.js new file mode 100644 index 0000000000000000000000000000000000000000..e1847ef09dc3a6b548364186b08d10b850642621 --- /dev/null +++ b/lib/wsapi/ping.js @@ -0,0 +1,16 @@ +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ + +const db = require('../db.js'); + +exports.method = 'get'; +exports.writes_db = false; +exports.i18n = false; + +exports.process = function(req, res) { + db.ping(function(err) { + if (err) res.send("fail", 500); + else res.send("ok",200); + }); +}; diff --git a/tests/stalled-mysql-test.js b/tests/stalled-mysql-test.js index a0753552763a36b9a1f434c1986e47b64cee4ca8..cd40adba4c379ee97fa585626ba816ff46eb6cd7 100755 --- a/tests/stalled-mysql-test.js +++ b/tests/stalled-mysql-test.js @@ -77,6 +77,13 @@ suite.addBatch({ // now try all apis that can be excercised without further setup suite.addBatch({ + "ping": { + topic: wsapi.get('/wsapi/ping', {}), + "fails with 500 when db is stalled": function(err, r) { + // address info with a primary address doesn't need db access. + assert.strictEqual(r.code, 500); + } + }, "address_info": { topic: wsapi.get('/wsapi/address_info', { email: 'test@example.domain' @@ -154,6 +161,16 @@ addStallDriverBatch(false); var token = undefined; +suite.addBatch({ + "ping": { + topic: wsapi.get('/wsapi/ping', {}), + "works when database is unstalled": function(err, r) { + // address info with a primary address doesn't need db access. + assert.strictEqual(r.code, 200); + } + } +}); + suite.addBatch({ "account staging": { topic: wsapi.post('/wsapi/stage_user', { @@ -194,6 +211,13 @@ addStallDriverBatch(true); // test remaining wsapis suite.addBatch({ + "ping": { + topic: wsapi.get('/wsapi/ping', { }), + "fails": function(err, r) { + assert.strictEqual(r.code, 500); + } + }, + "account_cancel": { topic: wsapi.post('/wsapi/account_cancel', { }), "fails with 503": function(err, r) {