相信 pm2 这个工具只要在 FE 圈混过的人都略有耳闻,主从模式、集群模式、多进程、日志管理、内存监控…等都是由 pm2 完成,可以说使用 pm2 的 nodejs 应用才能被称为真正的 nodejs 应用。
乍一看很复杂的东西,上手应该很难吧,但其实不然,只要进行简单的配置即可开箱即用!
正文 包管理工具新纪元我们以往的文章都是一概采用 yarn 作为包管理工具进行演示,由于 pnpm 已经在国内被推流起来了,加上尤雨溪和 pnpm 进行了朋 ( p ) 友 ( y ) 交易,也把 vue-next / vite 迁移成了 pnpm 管理 (但不是全链路的 pnpm ,还掺杂了 yarn 的运行流程) ,故从今天开始,我们会主要使用 pnpm 进行演示。
pm2 起步首先要全局安装 pm2 :
pnpm add -g pm2
注意如果运行在 docker 内,可以把 pm2 在 COPY 进容器前安装在项目内:
pnpm add -D pm2关注配置文件
下一步我们开始对 pm2 启动进行配置,在 项目根目录 下运行配置初始化命令:
pm2 init simple
之后会在该项目根目录得到一个初始 pm2 配置文件 ecosystem.config.js :
// ./ecosystem.config.js
module.exports = {
apps : [{
name : "app1",
script : "./app.js"
}]
}
下面我们推荐一份配置:
// ./ecosystem.config.js
module.exports = {
apps: [
{
// 项目的名字,可任意
name: 'yyy',
// 项目启动的命令,可以为 js 文件,如:dist/index.js
// 或为实际 bash 命令,如此处:pnpm dev 等
script: 'pnpm dev',
// 项目运行的根目录
cwd: './',
// 是否在项目文件发生改动时重启项目:
// 一般情况我们或多或少都会读写项目里的文件,如生成 cache 等,故不允许重启
watch: false,
// 项目最小健康时间:我们这里认为该项目启动的 24h 内一定都是正常运行的,否则将产生 error 报错
min_uptime: '24h',
// 项目最大内存:当内存占用超过这个 limit 时将自动重启
max_memory_restart: '500M',
// 自动重启次数
max_restarts: 10,
// 每次尝试重启的间隔时间(毫秒)
restart_delay: 4000,
// 输出日志时的时间日期 prefix,每行日志前都会带上
log_date_format: 'YYYY-MM-DD HH:mm Z',
// 程序运行控制台的正常输出保存位置
out_file: './log/out.log',
// 程序运行错误日志保存位置
error_file: './log/error.log',
// 是否将多个 pid 的进程日志合并,我们不希望日志还要分开看,所以合并在一个文件查看即可
combine_logs: true,
},
],
}
关于更多配置项的说明,可查看官方说明文档:PM2 Configuration File
启动项目到此为止,我们的配置便结束,下面我们在服务器启动项目即可:
# 在项目根目录下执行 pm2 启动,并指定了配置文件位置 pm2 start ./ecosystem.config.js
此时 pm2 便会在后台运行保活我们的项目。
多场景下面我们考虑更多场景。
docker 部署如果你是 docker 部署,必须保证进程持续存活,因为正常执行 pm2 start 后会将该应用进程置于后景(后台),此时 docker 就会认为执行结束,容器 down 掉无法继续存活。
所以我们为了保持 docker 容器存活,必须将 pm2 执行的应用置于前景(前台)持续运行,此时需要做的一个变化即是将启动命令 pm2 替换为 pm2-docker 或 pm2-runtime :
pm2-docker start ./ecosystem.config.js # 或 pm2-runtime start ./ecosystem.config.js
全部 pm2 可用主命令可见: pm2 / bin
多实例部署既然使用了 docker,集群部署也是一个重要场景,为了负载均衡,我们需使用 cluster mode ,在配置文件内额外加上 cluster 配置:
// ./ecosystem.config.js
// 加上以下两行配置
module.exports = {
apps: [
{
instances: -1,
exec_mode: 'cluster',
},
],
}
由此一来,便可在多个 pid 负载均衡请求。
关于 cluster mode 的更多说明,可参见:PM2 Cluster Mode
日志旋转正常情况我们的程序执行日志会全部输出于一个文件,若配置了 out_file 选项,会全部输出于该文件,大小变大后十分不友好,所以我们可以进行日志旋转,安装 pm2 套件:
pm2 install pm2-logrotate
全部配置可参见:pm2-logrotate
当 pm2 具有此模块时,会默认:
-
每 30s 检测一次日志大小,最大默认 10M ,大于此 size 将进行分包。
-
每天 00:00 强制进行旋转。
-
假如你的 out_file 指定为 ./log/out.log ,则每次旋转将产生 ./log/out__YYYY-MM-DD_HH-mm-ss.log 文件。
如果需要更改以上配置,可参见该模块的 配置说明 ,并在运行前进行命令行设定:
# 设定最大日志 size 为 1M pm2 set pm2-logrotate:max_size 1M
注:若在容器中,记得在运行前把该 pm2 模块安装到容器内,可以考虑使用 shell 脚本、script hook、或者直接 build 到容器固化。
其他通常情况下,pm2 只是一个助力 nodejs 保活的工具,真正要高并发还需要你拥有惊人的硬件支持,并进行大量的分布式多活部署。
因为,nodejs 不是一个 “好后端”,和 Go / Java 相比,还是有点捉襟见肘了。



