Added metrics + monitoring to DatabaseStateManager

ref https://linear.app/tryghost/issue/DEV-32/remove-migratejs-script

- we want to switch to using this code path instead of our separate
  migrate.js script on Pro
- the main things we're missing are metrics + monitoring for when things
  go wrong, so this adds that to the DatabaseStateManager
- this allows us to eventually delete the script without losing
  functionality
This commit is contained in:
Daniel Lockyer 2024-10-15 10:24:13 +02:00 committed by Daniel Lockyer
parent f982bbe9fa
commit 1c9e55cf7b

View File

@ -1,6 +1,9 @@
const KnexMigrator = require('knex-migrator'); const KnexMigrator = require('knex-migrator');
const errors = require('@tryghost/errors'); const errors = require('@tryghost/errors');
const logging = require('@tryghost/logging'); const logging = require('@tryghost/logging');
const metrics = require('@tryghost/metrics');
const sentry = require('../../../shared/sentry');
const states = { const states = {
READY: 0, READY: 0,
@ -61,9 +64,14 @@ class DatabaseStateManager {
// CASE: database connection errors, unknown cases // CASE: database connection errors, unknown cases
let errorToThrow = error; let errorToThrow = error;
if (!errors.utils.isGhostError(errorToThrow)) { if (!errors.utils.isGhostError(errorToThrow)) {
errorToThrow = new errors.InternalServerError({message: errorToThrow.message, err: errorToThrow}); errorToThrow = new errors.InternalServerError({
code: 'DATABASE_ERROR',
message: errorToThrow.message,
err: errorToThrow
});
} }
sentry.captureException(errorToThrow);
throw errorToThrow; throw errorToThrow;
} }
} }
@ -79,11 +87,25 @@ class DatabaseStateManager {
} }
if (state === states.NEEDS_INITIALISATION) { if (state === states.NEEDS_INITIALISATION) {
const beforeInitializationTime = Date.now();
await this.knexMigrator.init(); await this.knexMigrator.init();
metrics.metric('migrations', {
value: Date.now() - beforeInitializationTime,
type: 'initialization'
});
} }
if (state === states.NEEDS_MIGRATION) { if (state === states.NEEDS_MIGRATION) {
const beforeMigrationTime = Date.now();
await this.knexMigrator.migrate(); await this.knexMigrator.migrate();
metrics.metric('migrations', {
value: Date.now() - beforeMigrationTime,
type: 'migrations'
});
} }
state = await this.getState(); state = await this.getState();
@ -92,9 +114,14 @@ class DatabaseStateManager {
} catch (error) { } catch (error) {
let errorToThrow = error; let errorToThrow = error;
if (!errors.utils.isGhostError(error)) { if (!errors.utils.isGhostError(error)) {
errorToThrow = new errors.InternalServerError({message: errorToThrow.message, err: errorToThrow}); errorToThrow = new errors.InternalServerError({
code: 'DATABASE_ERROR',
message: errorToThrow.message,
err: errorToThrow
});
} }
sentry.captureException(errorToThrow);
throw errorToThrow; throw errorToThrow;
} }
} }