Node.js logger Winston / Morgan

sprinkler dev·2021년 12월 14일
0

git repo : winston / morgan

Winston

  • 콘솔, 파일 등 다양한 출력형식을 지원하는 간단한 범용 로깅 라이브러리
  • 아래와 같이 총 7가지 로그 레벨이 정의되어 있음
const levels = {
	error: 0,
	warn: 1,
	info: 2,
	http: 3,
	verbose: 4,
	debug: 5,
	silly: 6
};

사용예

  • 아래 예시 코드처럼 직접 로거를 만들어 사용하는 것이 추천됨
  • 아래는 에러와 일반 로그를 다른 파일로 분리하고 NODE_ENV 환경변수가 'production'이 아닐 때, 즉 개발/테스트 모드일 때는 콘솔에 출력을 하고 production 환경에서는 파일 출력만 하는 예제 코드
const winston = require('winston');

const logger = winston.createLogger({
  level: 'info',
  format: winston.format.json(),
  defaultMeta: { service: 'user-service' },
  transports: [
    //
    // - Write all logs with importance level of `error` or less to `error.log`
    // - Write all logs with importance level of `info` or less to `combined.log`
    //
    new winston.transports.File({ filename: 'error.log', level: 'error' }),
    new winston.transports.File({ filename: 'combined.log' }),
  ],
});

//
// If we're not in production then log to the `console` with the format:
// `${info.level}: ${info.message} JSON.stringify({ ...rest }) `
//
if (process.env.NODE_ENV !== 'production') {
  logger.add(new winston.transports.Console({
    format: winston.format.simple(),
  }));
}

winston-daily-rotate-file

  • 로그 파일을 날짜, 크기제한 등에 따라 분리할 수 있게 하는 모듈

사용예

const logger = winston.createLogger({
  level: 'info',
  transports: [
    new winston.transports.Console(),
    new winston.transports.File({ filename: 'combined.log' })
  ]
});

//
// Replaces the previous transports with those in the
// new configuration wholesale.
//
const DailyRotateFile = require('winston-daily-rotate-file');
logger.configure({
  level: 'verbose',
  transports: [
    new DailyRotateFile(opts)
  ]
});

같은 타입의 다중 출력예

  • info, error 레벨 로그를 각각 다른 파일로 출력
const logger = winston.createLogger({
  transports: [
    new winston.transports.File({
      filename: 'combined.log',
      level: 'info'
    }),
    new winston.transports.File({
      filename: 'errors.log',
      level: 'error'
    })
  ]
});

Morgan

  • HTTP 리퀘스트 로깅 미들웨어

사용예

const morgan = require('morgan');

// Using a predefiend format string
morgan('tiny');

// Using format string of predefined tokens
morgan(':method :url :status :res[content-length] - :response-time ms');

// Using a custom format function
morgan(function (tokens, req, res) {
	return [
		tokens.method(req, res),
		tokens.url(req, res),
		tokens.status(req, res),
		tokens.res(req, res, 'content-length'), '-',
		tokens.['response-time'](req, res), 'ms'
	].join(' ');
});

사전 정의된 포맷

  • combined, common, dev, short, tiny 다섯 가지 포맷이 정의돼 있음
combined
:remote-addr - :remote-user [:date[clf]] ":method :url HTTP/:http-version" :status :res[content-length] ":referrer" ":user-agent"

common
:remote-addr - :remote-user [:date[clf]] ":method :url HTTP/:http-version" :status :res[content-length]

dev
:method :url :status :response-time ms - :res[content-length]

short
:remote-addr :remote-user :method :url HTTP/:http-version :status :res[content-length] - :response-time ms

tiny
:method :url :status :res[content-length] - :response-time ms

winston + morgan 함께 사용

  • morgan 메소드의 두번째 인자에 winston logger를 넣으면 morgan에서 출력하는 로그가 winston으로 정의한 로거에 출력됨
const morgan = require('morgan');
const logger = require(WINSTON_LOGGER_LOCATION);

morgan('tiny', { logger });

새로운 토큰 생성

  • morgan.token() 메소드를 호출해 새로운 토큰을 정의할 수 있음
morgan.token('type', function (req, res) { return req.headers['content-type'] });
profile
2년차 백엔드 개발자

0개의 댓글