fix(reliability): multer-ошибки, process-хендлеры, анти-гонка питомца, flashcards (Спринт2)
- errorHandler: MulterError → 413 «слишком большой» / 400 (а не 500). - server: process.on(unhandledRejection/uncaughtException) — глобальная страховка с логированием, процесс не падает от единичной асинхронной ошибки. - pet: атомарный CAS на кулдаунах petAction/starCatch/feedPet (UPDATE ... WHERE last IS ?, начисление только при changes=1) — нет двойного начисления при параллельных запросах. Проверено на семантике node:sqlite. - assistant.flashcardsFromText: await callLLMFailover в try/catch → 502 вместо необработанного отклонения промиса. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -549,3 +549,12 @@ function shutdown(signal) {
|
||||
}
|
||||
process.on('SIGTERM', () => shutdown('SIGTERM'));
|
||||
process.on('SIGINT', () => shutdown('SIGINT'));
|
||||
|
||||
/* ── Глобальная страховка: не валим процесс на единичной асинхронной ошибке.
|
||||
Логируем (с requestId недоступен здесь — это вне цикла запроса) и продолжаем. */
|
||||
process.on('unhandledRejection', (reason) => {
|
||||
logger.error('unhandledRejection', { err: (reason && reason.message) || String(reason), stack: reason && reason.stack });
|
||||
});
|
||||
process.on('uncaughtException', (err) => {
|
||||
logger.error('uncaughtException', { err: err && err.message, stack: err && err.stack });
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user