温馨提示×

Debian中Node.js日志如何进行故障排查

小樊
35
2025-12-30 02:37:58
栏目: 编程语言

Debian 上 Node.js 日志故障排查实操指南

一 定位日志来源与快速查看

  • 应用日志:优先在项目目录的 logs/ 或自定义目录(如 /var/log/myapp//var/log/nodejs/)查找;若使用日志库(如 winston、morgan、pino),以库配置为准。快速查看命令:tail -f logs/app.logless logs/error.loggrep -n “ERROR” logs/*.log
  • systemd 服务日志:使用 journalctl -u nodeapp.service -f(实时跟踪),或按时间过滤:journalctl -u nodeapp.service --since “2025-11-30 10:00:00”
  • 系统日志:全局检索 /var/log/syslog(如:grep -i node /var/log/syslog)。
  • 内核与资源线索:dmesg | grep -i node 可发现 OOM、cgroup 限制等内核事件。
  • 运行时调试:临时开启模块调试输出 DEBUG= node your-app.js*(生产慎用,避免性能与信息泄露)。

二 提高日志可读性与信息量

  • 使用结构化日志库:选择 Winston / Pino / Bunyan,便于多目标输出(控制台、文件、远程)与后续检索分析。
  • 配置合理的日志级别:开发环境用 debug/info,生产环境用 warn/error;通过环境变量控制,如 WINSTON_LEVEL=debugPINO_LEVEL=debug
  • 统一格式与时间戳:建议包含 timestamp、level、message、stack;JSON 格式便于聚合与检索。
  • 请求日志与错误分离:Express + morgan 记录 HTTP 请求;错误单独写入 error.log,避免淹没关键异常。
  • 可读性增强:开发时用 pino-pretty / bunyan-pretty 美化输出;生产保持 JSON 便于机器处理。

三 常见错误模式与日志线索

  • 未捕获异常与未处理的 Promise 拒绝:现象为进程意外退出、堆栈不完整或仅有 UnhandledPromiseRejectionWarning。线索:应用日志缺少 try/catch 堆栈。处置:添加全局监听并记录完整堆栈,必要时 process.exit(1),交由 systemd 重启。
  • 依赖与配置错误:现象为启动失败、MODULE_NOT_FOUND、连接字符串错误。线索:应用日志含依赖或配置读取失败。处置:核对 node_modules.env 与配置路径,必要时回滚版本或修正配置。
  • HTTP 层异常:现象为大量 4xx/5xx、接口超时。线索:morgan 输出请求路径、状态码、耗时;结合业务日志定位上游/下游问题。
  • 资源与内核限制:现象为进程被系统终止、间歇性失败。线索:dmesg 出现 OOM 或 cgroup 限制;syslog 有 killed process 记录。处置:检查内存/CPU、调整服务资源限制或优化代码内存占用。

四 高效排查命令与最小实践示例

  • 常用命令清单:
    • 实时跟踪服务日志:journalctl -u nodeapp.service -f
    • 过滤关键字:grep -n “ERROR|Exception” /var/log/myapp/*.log
    • 最近错误并高亮:tail -n 200 /var/log/myapp/error.log | grep -E --color=auto “ERROR|WARN”
    • 内核与驱动线索:dmesg -T | tail -n 50
    • 进程崩溃回溯:查看 syslog 中服务停止与 OOM 信息
  • 最小实践示例(Express + Winston + Morgan):
    • 安装依赖:npm i express morgan winston
    • 日志配置(logger.js)
      • const winston = require(‘winston’);
        const { combine, timestamp, json } = winston.format;
        const logger = winston.createLogger({
        level: process.env.LOG_LEVEL || ‘info’,
        format: combine(timestamp(), json()),
        transports: [
        new winston.transports.File({ filename: ‘logs/error.log’, level: ‘error’ }),
        new winston.transports.File({ filename: ‘logs/combined.log’ }),
        new winston.transports.Console()
        ]
        });
        module.exports = logger;
    • HTTP 请求日志(app.js)
      • const express = require(‘express’);
        const morgan = require(‘morgan’);
        const logger = require(‘./logger’);
        const app = express();
        app.use(morgan(‘combined’, { stream: { write: msg => logger.info(msg.trim()) } }));
        app.get(‘/error’, () => { throw new Error(‘boom’); });
        app.use((err, req, res, next) => {
        logger.error({ err: err.stack }, ‘uncaught error’);
        res.status(500).send(‘Internal Server Error’);
        });
        app.listen(3000, () => logger.info(‘Server listening on 3000’));
    • 全局异常兜底
      • process.on(‘unhandledRejection’, (reason) => {
        logger.error({ reason }, ‘Unhandled Rejection’);
        process.exit(1); // 交由 systemd 重启
        });
    • 运行与观察:LOG_LEVEL=debug node app.js,访问 /error,观察控制台、logs/error.loglogs/combined.log 的输出。

五 稳定运行与长期改进

  • 日志轮转与容量控制:使用 logrotate 管理日志文件大小与保留周期,避免磁盘被占满。
  • 监控与告警:结合 Prometheus + Grafana 监控错误率、延迟与资源使用;对 ERROR 关键字设置告警。
  • 集中化与结构化:将日志汇聚到 ELK/Datadog/New Relic 等平台,统一检索、可视化与链路追踪。

0