node項目在pm2 cluster模式下定時任務重復執行的問題


原文鏈接: https://www.cnblogs.com/yalong/p/15601391.html

背景:

有個需求,需要每天刪除過期的數據,所以用到了定時任務,但是發現定時任務每次都是執行多次,原來是pm2 的 cluster模式導致的,最終還是解決了,在此記錄

一. 定時任務怎么寫

使用 node-schedule, githuib地址是: https://github.com/node-schedule/node-schedule

node-schedule 更多使用可以參考這個https://www.cnblogs.com/zhongweiv/p/node_schedule.html

我的項目是koa2,這里以每3秒打印為例,具體使用就是在app.js 中添加如下代碼

const schedule = require("node-schedule");
const job = schedule.scheduleJob("*/3 * * * * *", function () {
  console.log('每3秒我執行一次,啦啦啦' + new Date())
});

如下圖:

二.復現問題

1.使用pm2 的 cluster模式啟動服務

我的pm2 的配置文件,pm2.josn 內容如下:

{
  "apps": [
    {
      "name": "koa-test",
      "script": "bin/www",
      "cwd": "",
      "exec_mode": "cluster",
      "instances": 0,
      "autorestart": true,
      "node_args": [],
      "args": [],
      "env": {
        "NODE_ENV": "production"
      }
    }
  ]
}

執行 pm2 start ./pm2.json 啟動服務,如下圖

執行pm2 log 查看打印日志,如下圖

可以看到,每3秒后,一下子打印8次,就是說定時任務是重復執行的

三.解決問題

如下圖

可以看到 pm2 實例的id是不重復的, 那么在某個指定id下執行定時任務不就ok了
這個id的屬性獲取方式是 process.env.NODE_APP_INSTANCE

在項目中測試

const job = schedule.scheduleJob("*/3 * * * * *", function () {
  console.log(process.env.NODE_APP_INSTANCE)
});

再查看pm2 log 就能看到打印的就是pm2 中每個 worker 的id值

最終代碼如下:

const job = schedule.scheduleJob("*/3 * * * * *", function () {
  if (process.env.NODE_APP_INSTANCE === '0') {
    console.log('每3秒我執行一次,啦啦啦' + new Date())
  }
});

結果如下圖所示,問題得以解決

分析總結

定時任務重復執行的原因是pm2 的cluster 模式創建的每個worker進程,是同步執行的,所以就導致了重復執行,
Node.js—Cluster多進程模式與PM2的實現可以參考這里: https://www.cnblogs.com/xingchong/p/13183162.html


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM