UNPKG

@vitaly-yosef/node-smart-logger

Version:

Universal logger for Node.js applications with support for both ESM and CommonJS. It provides advanced features, such as structured logging in JSON format, integration with AWS CloudWatch Logs, and contextual logging.

296 lines (224 loc) 13.8 kB
# Node Smart Logger [![npm version](https://img.shields.io/npm/v/@vitaly-yosef/node-smart-logger.svg)](https://www.npmjs.com/package/@vitaly-yosef/node-smart-logger) [![Downloads](https://img.shields.io/npm/dm/@vitaly-yosef/node-smart-logger.svg)](https://www.npmjs.com/package/@vitaly-yosef/node-smart-logger) [![Build Status](https://github.com/Yosef-fullstack/node-smart-logger/actions/workflows/main.yml/badge.svg)](https://github.com/Yosef-fullstack/node-smart-logger/actions) [![Coverage Status Coveralls](https://coveralls.io/repos/github/Yosef-fullstack/node-smart-logger/badge.svg?branch=master)](https://coveralls.io/github/Yosef-fullstack/node-smart-logger?branch=master) [![Coverage Status Codecov](https://codecov.io/gh/yosef-fullstack/node-smart-logger/branch/master/graph/badge.svg)](https://codecov.io/gh/yosef-fullstack/node-smart-logger/branch/master/graph/badge.svg) [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT) Универсальный модуль логирования с расширенными функциями, включая структурированное логирование в формате JSON, интеграцию с AWS CloudWatch Logs и контекстное логирование. Его можно использовать как для ESM, так и для CommonJS. ## Возможности - Структурированное логирование в формате JSON - Гибкий выбор формата логов (текст для разработки, JSON для продакшена) - Ротация лог-файлов с компрессией - Интеграция с AWS CloudWatch Logs - Контекстное логирование (trace ID, request ID, operation ID, device ID, user ID) - Расширенные уровни логирования и цвета для лучшей видимости и фильтрации - Логирование метаданных (имя хоста, окружение, имя сервиса) - Middleware для HTTP-запросов с автоматическим трейсингом - Middleware для обработки ошибок - Совместимость с модулями ESM и CommonJS (import/require) ## Новое в версии 1.3.0 ### Добавлено - **Ограничение частоты логов**: Защита от переполнения (1000 логов/секунду) - **Корректное завершение**: Гарантированная запись всех логов перед завершением - **Улучшенная обработка ошибок**: Более информативные сообщения и трассировка стека - **Расширенное тестирование**: Полное покрытие тестами всех функций ### Изменено - Метод resetRateLimit теперь принимает необязательный параметр timestamp - Улучшено форматирование логов и работа с контекстом ### Исправлено - Исправлена работа с контекстом в асинхронных операциях - Улучшены типы TypeScript - Различные исправления ошибок и улучшение производительности ## Установка ```bash # Используя npm npm install @vitaly-yosef/node-smart-logger # Используя yarn yarn add @vitaly-yosef/node-smart-logger # Используя pnpm pnpm add @vitaly-yosef/node-smart-logger ``` ## Использование ### Базовое использование ```javascript import { createLogger } from '@vitaly-yosef/node-smart-logger'; // Создание экземпляра логгера с именем сервиса и путем к лог-файлам const logger = createLogger('my-service', './logs'); // Логирование на разных уровнях logger.debug('Отладочное сообщение'); logger.info('Информационное сообщение'); logger.warn('Предупреждение'); logger.error('Сообщение об ошибке'); logger.alert('Критическое предупреждение'); ``` ### Контекстное логирование ```javascript import { createLogger, setLoggerContext, clearLoggerContext, generateLoggerTraceId } from '@vitaly-yosef/node-smart-logger'; const logger = createLogger('my-service', './logs'); // Генерация и установка контекста const traceId = generateLoggerTraceId(); setLoggerContext({ traceId, deviceId: 'device-123' }); // Логи будут содержать контекст logger.info('Обработка данных устройства'); // Очистка контекста после завершения операции clearLoggerContext(); ``` Дополнительные примеры контекстного логирования. ```javascript const { createLogger, setLoggerContext, clearLoggerContext } = require('@vitaly-yosef/node-smart-logger'); const logger = createLogger('my-service', './logs'); function processDevice(deviceId, data) { setLoggerContext({ operationId: 'process-device', deviceId: deviceId }); try { logger.info(`Обработка данных устройства`); // Лог будет содержать deviceId и operationId // ... обработка данных ... logger.info(`Данные устройства успешно обработаны`); return result; } catch (error) { logger.error(`Ошибка обработки данных устройства: ${error.message}`); throw error; } finally { // Очистка контекста после завершения операции clearLoggerContext(); } } ``` Или более удобный способ с использованием метода ```withOperationContext```. ```javascript const { createLogger } = require('@vitaly-yosef/node-smart-logger'); const logger = createLogger('my-service', './logs'); function processDevice(deviceId, data) { return logger.withOperationContext( { operationId: 'process-device', deviceId }, () => { logger.info(`Обработка данных устройства`); // с контекстом // ... обработка данных ... logger.info(`Данные устройства успешно обработаны`); // с контекстом return result; } ); } ``` > **Примечание**: Метод `withOperationContext` возвращает результат выполнения callback-функции, если она была передана, или сгенерированный operation ID, если callback не был предоставлен. Это позволяет легко интегрировать управление контекстом с существующим потоком кода. ### HTTP-логгер с middleware для трейсинга ```javascript import express from 'express'; import { createLogger, createHttpLogger, createErrorLogger } from '@vitaly-yosef/node-smart-logger'; const app = express(); const logger = createLogger('api-service', './logs'); // Middleware для логирования HTTP-запросов с трейсингом app.use(createHttpLogger(logger)); // Middleware для логирования ошибок app.use(createErrorLogger(logger)); app.get('/api/devices', (req, res) => { // Контекст уже установлен в middleware logger.info('Получение списка устройств'); // Добавление дополнительного контекста logger.setContext({ userId: req.user?.id }); // Логика обработки запроса res.json({ devices: [] }); }); app.listen(3000, () => { logger.info('Сервер запущен на порту 3000'); }); ``` ### Интеграция с AWS CloudWatch Logs Для включения логирования в AWS CloudWatch установите следующие переменные окружения: ``` AWS_CLOUDWATCH_ENABLED=true AWS_CLOUDWATCH_GROUP=IoTMonSys-ServiceName AWS_CLOUDWATCH_STREAM=instance-name AWS_REGION=us-east-1 AWS_ACCESS_KEY_ID=your_access_key AWS_SECRET_ACCESS_KEY=your_secret_key ``` > **Примечание**: При использовании `LOG_FORMAT=text` с `AWS_CLOUDWATCH_ENABLED=true`, ваши локальные логи будут в текстовом формате, но CloudWatch будет получать логи в формате JSON для лучшего анализа и фильтрации. ## Уровни логирования - `alert`: 0 - Критические ошибки, требующие немедленных действий - `error`: 1 - Ошибки, нарушающие работу приложения - `warn`: 2 - Предупреждения, не мешающие работе приложения - `info`: 3 - Информационные сообщения о работе приложения - `http`: 4 - Логирование HTTP-запросов - `debug`: 5 - Отладочная информация ## Форматы логов Логгер поддерживает два формата вывода, которые можно настроить через переменную окружения `LOG_FORMAT`: ### Текстовый формат (`LOG_FORMAT=text`) Человекочитаемый формат с цветами в консоли, идеально подходит для разработки: ```log 2025-06-12 17:14:51:1451 [udp-listener] INFO [trace:abc123] [operation:process-data]: Данные устройства успешно обработаны ``` В консоли этот формат отображается с цветами: - Временная метка: серый - Имя сервиса (`[udp-listener]`): синий - Уровень логирования (`INFO`): зеленый для info, желтый для warn, красный для error - Контекст (`[trace:abc123]`): фиолетовый - Сообщение: белый Это делает логи более читаемыми и позволяют быстро выделять важную информацию. ### JSON формат (`LOG_FORMAT=json`) Машиночитаемый формат, идеально подходит для продакшена и интеграции с CloudWatch: ```json { "timestamp": "2025-06-12T17:14:51.451Z", "level": "info", "message": "Данные устройства успешно обработаны", "service": "udp-listener", "hostname": "server-name", "environment": "production", "traceId": "abc123", "operationId": "process-data", "deviceId": "device-456" } ``` > **Важно**: Логи CloudWatch всегда отправляются в формате JSON независимо от настройки `LOG_FORMAT` для обеспечения правильного парсинга и анализа в AWS CloudWatch. ## Тестирование Проект использует Jest для тестирования. Тесты находятся в директории `src/__tests__`. ### Запуск тестов ```bash # Запуск всех тестов npm test # Запуск тестов с покрытием npm test -- --coverage ``` ### Структура тестов Тесты структурированы для проверки: - Основной функциональности логгера - Управления контекстом - HTTP middleware - Middleware обработки ошибок ### Мокирование зависимостей При написании тестов для кода, использующего этот логгер, вам может потребоваться его мокировать. Вот пример: ```javascript // Мок модуля логгера jest.mock('@vitaly-yosef/node-smart-logger', () => { return { createLogger: jest.fn().mockReturnValue({ info: jest.fn(), error: jest.fn(), warn: jest.fn(), debug: jest.fn(), setContext: jest.fn(), getContext: jest.fn(), clearContext: jest.fn(), generateTraceId: jest.fn() }), createHttpLogger: jest.fn().mockReturnValue((req, res, next) => next()), createErrorLogger: jest.fn().mockReturnValue((err, req, res, next) => next(err)) }; }); ``` ## Настройки Модуль логирования использует следующие переменные окружения: | Переменная | Описание | Значение по умолчанию | |------------|----------|----------------------| | NODE_ENV | Окружение (development/production) | development | | LOG_FORMAT | Формат логов (text/json) | text для development, json для production | | AWS_CLOUDWATCH_ENABLED | Включить отправку логов в CloudWatch | false | | AWS_CLOUDWATCH_GROUP | Имя группы логов CloudWatch | - | | AWS_CLOUDWATCH_STREAM | Имя потока логов CloudWatch (по умолчанию: hostname-date) | - | | AWS_REGION | Регион AWS | - | | AWS_ACCESS_KEY_ID | ID ключа доступа AWS | - | | AWS_SECRET_ACCESS_KEY | Секретный ключ доступа AWS | - |