nest日志包pino、winston配置-懒人的折腾
nest日志
三种node服务端日志选型
- winston
- pino
- log4js
2023年5月23日
看star数:winston > pino > log4js
使用体验:
- pino 格式简洁,速度快,支持输入日志到任意数据库,日志暂无自动清理(可能是我方式不对?知道的朋友评论下告诉我,十分感谢~)
- winston 通用,稳定,日志可自动清理。
- log4js 不知为啥,不想使用,除非你劝我。
pino
目前使用 pino
npm install pino nestjs-pino pino-http
npm install nanoid
npm install pino-pretty -D
npm install pino-roll -D
pino-pretty: 格式化用
pino-roll: 日志,设置文件大小,分割周期,日志名。
特点:
- Pino的内部架构基于Worker Threads
- 配置简单
- 支持日志类型指定输出到不同文件(会导致速度慢)
- 支持输出日志到任意数据库中
问题:日志需要自己做定时任务清理,避免占用内存。
main.ts
import { Logger } from 'nestjs-pino';
const app = await NestFactory.create<NestExpressApplication>(AppModule, {bufferLogs: true, // 使用外部的日志包pino});app.useLogger(app.get(Logger));app.flushLogs();
logger.config.ts
import { nanoid } from 'nanoid';
import type { Request } from 'express';
import { IncomingMessage } from 'http';
import type { Params } from 'nestjs-pino';
import { multistream } from 'pino';
import type { ReqId } from 'pino-http';
import { join } from 'path';
import { format } from 'date-fns';
const passUrl = new Set(['./health']);
export const loggerOptions: Params = {pinoHttp: [{// https://getpino.io/#/docs/api?id=timestamp-boolean-functionquietReqLogger: true,genReqId: (req: IncomingMessage): ReqId =>(<Request>req).header('X-Request-id') || nanoid(),...(process.env.NODE_ENV === 'production'? {// https://www.npmjs.com/package/pino-rolllevel: 'error',transport: {target: 'pino-roll',options: {file: join('logs', 'log'),size: '10m',// 周期frequency: 'daily',mkdir: true,extension: `.${format(new Date(), 'yyyy-MM-dd')}.json`,},},}: {level: 'debug',transport: {// https://github.com/pinojs/pino-prettytarget: 'pino-pretty',options: { sync: true, colorize: true },// options: { sync: true, singleLine: true, colorize: true }, // 生产环境再设置压缩为一行},}),autoLogging: {ignore: (req: IncomingMessage) =>passUrl.has((<Request>req).originalUrl),},},multistream([{ level: 'debug', stream: process.stdout },{ level: 'error', stream: process.stdout },{ level: 'fatal', stream: process.stdout },],{ dedupe: true }, // 删除重复输出),],
};
其他设置模式,不如上面的设置,少了日志分割和文件大小配置,但pino还有流操作,里面可以写逻辑,自己写怎么分割日志或者限制文件大小等,等于自配。
// 1. pino/file
const file =process.cwd() + `/logs/log-${format(new Date(), 'yyyy-MM-dd')}.json`;
{level: 'info',transport: {target: 'pino/file',options: {destination: file, // 1 是直接输出, 2是错误时输出,其他为自己设置的目录文件mkdir: true,},},
}
// 使用内置的pino/file传输和使用pino.destination的区别在于,pino.destination在主线程中运行,而pino/file在工作线程中设置pino.destimation// 2. pino/file
target: 'pino-pretty',
使用 winston
- [nest-winston][nest-winston] 日志记录
- [winston-daily-rotate-file][winston-daily-rotate-file] 配置生产环境日志
npm install --save nest-winston winston
npm install winston-daily-rotate-file
采用[bootstrap配置方式][replacing-the-nest-logger-also-for-bootstrapping]
main.ts
const app = await NestFactory.create<NestExpressApplication>(AppModule, {logger: WinstonModule.createLogger({instance: createLogger({ ...loggerOptions }),}),
});
logger.config.ts
import * as winston from 'winston';
import { utilities as nestWinstonModuleUtilities } from 'nest-winston';
import DailyRotateFile from 'winston-daily-rotate-file';
const format = (label?: string) => {switch (label) {case 'isDev':return {format: winston.format.combine(winston.format.timestamp(),winston.format.ms(),nestWinstonModuleUtilities.format.nestLike('nestBk', {colors: true,prettyPrint: true,}),),};default:return {format: winston.format.combine(winston.format.timestamp(),winston.format.ms(),),};}
};
const prodLoggerConfig = [new DailyRotateFile({level: 'warn',filename: 'nestBk-%DATE%.log',dirname: 'logs',datePattern: 'YYYY-MM-DD-HH',maxSize: '20m',maxFiles: '14d',zippedArchive: true,...format(),}),new DailyRotateFile({level: 'info',filename: 'info-%DATE%.log',dirname: 'logs',datePattern: 'YYYY-MM-DD-HH',maxSize: '20m',maxFiles: '14d',zippedArchive: true,...format(),}),
];export const loggerOptions = {transports: [new winston.transports.Console({level: 'info',...format('isDev'),}),...(IsProMode ? prodLoggerConfig : []),],
};
使用时
xxx.module.ts
providers: [CatsService, Logger],
xxx.controller.ts
import { Logger } from '@nestjs/common';private readonly logger: Logger,this.logger.log('请求成功');this.logger.warn('请求警告');this.logger.error('请求错误');

样式没啥变化(反而喜欢pino的简洁样式)
主要是多了个自动到期删除的配置,不用自己手动删除日志

QA:
- nanoid esm 问题,直接降级处理
官方issues
“nanoid”: “^.4.x.x” => “nanoid”: “^3.3.6”,
参考
相关文章:
nest日志包pino、winston配置-懒人的折腾
nest日志 三种node服务端日志选型 winstonpinolog4js 2023年5月23日 看star数:winston > pino > log4js 使用体验: pino 格式简洁,速度快,支持输入日志到任意数据库,日志暂无自动清理(可能是我…...
一文看懂增值税发票识别OCR:从技术原理到 API Java 示例代码接入
引言 增值税发票识别OCR API是一项重要的技术创新,它在如今信息化的商业环境中发挥着重要作用。通过利用该API,企业和机构能够实现增值税发票的自动化识别和信息提取,从而在财务管理、票据核对、报销流程等方面带来许多好处。 本文将详细介…...
消息队列对比
目录 什么是消息队列 常用的消息队列工具对比 1 、ActiveMQ 2 、RabbitMQ 3、Kafka 4、 RocketMQ 什么是消息队列 消息队列是分布式应用间交换信息的重要组件,消息队列可驻留在内存或磁盘上, 队列可以存储消息直到它们被应用程序读走。通过消息队列࿰…...
Ceph对象存储的基本概念,使用以及优点
Ceph对象存储的基本概念,使用以及优点 Ceph是一种基于分布式架构的对象存储系统,它可以提供高可靠性、高扩展性和高性能的存储服务。这种存储系统可以用于处理大量的数据,例如大型数据库、云存储、视频流、图像数据等。Ceph对象存储系统的基…...
工业互联网UWB定位系统源码,支持自定义开发
工厂人员定位系统,采用UWB定位技术,通过在厂区内部署一定数量的定位基站,以及为人员、车辆、物资佩戴标签卡的形式,实时获取人员精确位置,精度高达10cm。 文末获取联系 工厂人员定位系统可实现物资/车辆实时定位&#…...
VIC模型教程
详情点击链接:RVIC模型融合实践技术应用及未来气候变化模型预测 一:VIC模型的原理与特点 1.VIC模型各模块的主要原理 2.VIC模型的特点及优势 3.VIC模型的适用范围及其限制 4.VIC模型主要输入和输出文件解析案例一 :基于QGIS的VIC模型建模…...
软件著作权容易搞吗?
没有代码、材料,只有一个软件名字就能拿证,你说容易不… 当然这是对我们软著一级代理来说,每年申请下证几千个软著。下面说说下证要点给大家避坑。人群覆盖高新企业、大学生、大学老师、互联网公司。 软件著作权想要轻松下证,必…...
Mac打出特殊字符
optionq:œ ---------optionw:∑ optione: ---------optionr: optiont:† ---------optiony: optionu: ---------optionI:无 optiono: ---------optionP:π o…...
java设计模式之单例设计模式的前世今生
单例设计模式是什么? 单例设计模式是一种创建型模式,它保证一个类只有一个实例,并且该实例提供了全局访问点。这意味着即使在不同的地方,访问这个单例实例的代码得到的都是同一个对象。 单例模式的特点如下: - 保证…...
小航助学2023年3月GESP_C++一级试卷(含题库答题软件账号)
GESP在线模拟训练系统请点击 电子学会-全国青少年编程等级考试真题Scratch一级(2019年3月)在线答题_程序猿下山的博客-CSDN博客_小航答题助手 答案:B 第1题以下不属于计算机输入设备的有( )。 A、键盘B、音箱C、鼠标D、传感器 …...
好程序员:女生学Java好学吗?女生学Java有什么优势?
小源经常会听到女生咨询适不适合学习Java开发的问题,提出这种问题归根结底还是缺乏性别自信,默认女性比男性弱。实际上这个问题并不存在,男女平等才是正确的思维,当然,也为了解开女生们的心结,这里好程序员…...
为Eclipse安装lombok插件
原生的Eclipse没有lombok插件,即使项目引入了lombok依赖也无法正常使用Data等常用标签。下面介绍一下如何手动为Eclipse添加lombok插件,具体操作步骤如下: (1)打开Download地址,点击页面中间的超链接下载最…...
spring-boot 实现接口转发服务,同时支持get 和 post等多种请求
spring-boot 实现接口转发服务,同时支持get 和 post等多种请求 (1)新建类:ProxyController.java package com.taobao.product.controller;import com.taobao.framework.HttpResult; import io.swagger.annotations.Api; import …...
About JDKFlightRecorder--人工翻译
JFR是什么 JDK Flight Recorder是一个工具,用于收集有关JVM以及在JVM上运行的Java程序的诊断和分析数据。 集成到Java虚拟机(JVM)中,使用默认设置时,性能影响小于1%。几乎不产生性能开销,因此即使在负载很…...
【计算机系统基础3】数据的存储与运算
【计算机系统基础3】数据的存储与运算 3.程序调试与实践:数据存储与运算3.1真值与机器数3.1.1整数的编码 3.2数据的存储3.3数组的对齐3.4数据类型的转换3.4.1整数之间的数据类型转换3.4.2整数与浮点数之间的转换3.4.3自动类型转换 3.5浮点数的表示和运算--IEEE 7543…...
【算法】快速排序
目录 核心思想: 过程: 演示: 第一趟: 第二趟: 代码: 核心思想: 从待排序列中取一个元素作为中心,所有比它小或相等的元素一律放在前面, 所有比它大的元素放在后面&…...
【移动端网页布局】流式布局案例 ③ ( 实现搜索栏功能 | 伪元素选择器 | 子绝父相 | 外边距塌陷处理 | 二倍精灵图处理方案 )
文章目录 一、搜索栏样式及核心要点1、实现效果2、自动伸缩搜索栏实现3、搜索栏父容器设置4、搜索栏左右两侧的按钮盒子5、搜索栏盒子6、二倍精灵图处理方案 二、完整代码示例1、HTML 标签结构2、CSS 样式3、展示效果 一、搜索栏样式及核心要点 1、实现效果 上一篇博客中 , 完成…...
【C++修炼之路】30.可变参数模板包装器
每一个不曾起舞的日子都是对生命的辜负 C11之可变参数模板&&包装器 前言一.可变参数模板的首次登场二.参数包展开2.1 递归函数方式展开参数包2.2 逗号表达式展开参数包 三.容器的emplace方法四.包装器4.1 什么是function4.2 function包装器的作用4.3 function的实际用途…...
Linux防火墙之firewalld基础
一、firewalld概述 firewalld防火墙是Centos7系统默认的防火墙管理工具,取代了之前的iptables防火墙,也是工作在网络层,属于包过滤防火墙。 firewalld和iptables都是用来管理防火墙的工具(属于用户态)来定义防火墙的…...
GitLab CI/CD
CI/CD 简介 CI/CD 简单来说就是可以自动化编译、测试、打包我们的代码。 GitLab CICD的使用 首先需要安装gitlab-runner。 在GitLab 中,runners 是运行 CI/CD 作业的代理。我们的对代码的作业都是在runner上去执行的。我们可以在本地、服务器、等任意一个联网设…...
Linux 文件类型,目录与路径,文件与目录管理
文件类型 后面的字符表示文件类型标志 普通文件:-(纯文本文件,二进制文件,数据格式文件) 如文本文件、图片、程序文件等。 目录文件:d(directory) 用来存放其他文件或子目录。 设备…...
AtCoder 第409场初级竞赛 A~E题解
A Conflict 【题目链接】 原题链接:A - Conflict 【考点】 枚举 【题目大意】 找到是否有两人都想要的物品。 【解析】 遍历两端字符串,只有在同时为 o 时输出 Yes 并结束程序,否则输出 No。 【难度】 GESP三级 【代码参考】 #i…...
基于数字孪生的水厂可视化平台建设:架构与实践
分享大纲: 1、数字孪生水厂可视化平台建设背景 2、数字孪生水厂可视化平台建设架构 3、数字孪生水厂可视化平台建设成效 近几年,数字孪生水厂的建设开展的如火如荼。作为提升水厂管理效率、优化资源的调度手段,基于数字孪生的水厂可视化平台的…...
DIY|Mac 搭建 ESP-IDF 开发环境及编译小智 AI
前一阵子在百度 AI 开发者大会上,看到基于小智 AI DIY 玩具的演示,感觉有点意思,想着自己也来试试。 如果只是想烧录现成的固件,乐鑫官方除了提供了 Windows 版本的 Flash 下载工具 之外,还提供了基于网页版的 ESP LA…...
python爬虫:Newspaper3k 的详细使用(好用的新闻网站文章抓取和解析的Python库)
更多内容请见: 爬虫和逆向教程-专栏介绍和目录 文章目录 一、Newspaper3k 概述1.1 Newspaper3k 介绍1.2 主要功能1.3 典型应用场景1.4 安装二、基本用法2.2 提取单篇文章的内容2.2 处理多篇文档三、高级选项3.1 自定义配置3.2 分析文章情感四、实战案例4.1 构建新闻摘要聚合器…...
SpringCloudGateway 自定义局部过滤器
场景: 将所有请求转化为同一路径请求(方便穿网配置)在请求头内标识原来路径,然后在将请求分发给不同服务 AllToOneGatewayFilterFactory import lombok.Getter; import lombok.Setter; import lombok.extern.slf4j.Slf4j; impor…...
Swagger和OpenApi的前世今生
Swagger与OpenAPI的关系演进是API标准化进程中的重要篇章,二者共同塑造了现代RESTful API的开发范式。 本期就扒一扒其技术演进的关键节点与核心逻辑: 🔄 一、起源与初创期:Swagger的诞生(2010-2014) 核心…...
Selenium常用函数介绍
目录 一,元素定位 1.1 cssSeector 1.2 xpath 二,操作测试对象 三,窗口 3.1 案例 3.2 窗口切换 3.3 窗口大小 3.4 屏幕截图 3.5 关闭窗口 四,弹窗 五,等待 六,导航 七,文件上传 …...
Vite中定义@软链接
在webpack中可以直接通过符号表示src路径,但是vite中默认不可以。 如何实现: vite中提供了resolve.alias:通过别名在指向一个具体的路径 在vite.config.js中 import { join } from pathexport default defineConfig({plugins: [vue()],//…...
Bean 作用域有哪些?如何答出技术深度?
导语: Spring 面试绕不开 Bean 的作用域问题,这是面试官考察候选人对 Spring 框架理解深度的常见方式。本文将围绕“Spring 中的 Bean 作用域”展开,结合典型面试题及实战场景,帮你厘清重点,打破模板式回答,…...
