Ответ 1
Вы можете перехватить сигналы и выполнить асинхронную задачу перед выходом. Примерно так будет вызывать функцию terminator() перед выходом (даже ошибка JavaScript в коде):
process.on('exit', function () {
// Do some cleanup such as close db
if (db) {
db.close();
}
});
// catching signals and do something before exit
['SIGHUP', 'SIGINT', 'SIGQUIT', 'SIGILL', 'SIGTRAP', 'SIGABRT',
'SIGBUS', 'SIGFPE', 'SIGUSR1', 'SIGSEGV', 'SIGUSR2', 'SIGTERM'
].forEach(function (sig) {
process.on(sig, function () {
terminator(sig);
console.log('signal: ' + sig);
});
});
function terminator(sig) {
if (typeof sig === "string") {
// call your async task here and then call process.exit() after async task is done
myAsyncTaskBeforeExit(function() {
console.log('Received %s - terminating server app ...', sig);
process.exit(1);
});
}
console.log('Node server stopped.');
}
Добавить детали, запрошенные в комментарии:
- Сигналы, объясненные из документации узла, эта ссылка относится к стандартным именам сигналов POSIX
- Сигналы должны быть строковыми. Тем не менее, я видел, что другие сделали проверку, поэтому могут быть некоторые другие неожиданные сигналы, о которых я не знаю. Просто хочу убедиться перед вызовом process.exit(). Я полагаю, что проверка все равно не займет много времени.
- для db.close(), я думаю, это зависит от используемого вами драйвера. Будь то синхронизация асинхронная. Даже если он асинхронный, и вам не нужно ничего делать после закрытия db, тогда все должно быть в порядке, потому что async db.close() просто генерирует событие close, и цикл обработки событий продолжит его обрабатывать независимо от того, завершился ли ваш сервер или нет.