如何停止node.js表示'npm start'的应用


100

您使用express v4.x构建node.js应用,然后通过npm start启动您的应用。我的问题是如何停止该应用程序?有npm停吗?

执行npm stop编辑以包含错误

/home/nodetest2# npm stop

> nodetest2@0.0.1 stop /home/nodetest2
> pkill -s SIGINT nodetest2

pkill: invalid argument for option 's' -- SIGINT

npm ERR! nodetest2@0.0.1 stop: `pkill -s SIGINT nodetest2`
npm ERR! Exit status 2

Answers:


66

是的,npm也提供了停止脚本:

npm help npm-scripts

prestop,stop,poststop:由npm stop命令运行。

在package.json中设置以上内容之一,然后使用 npm stop

npm help npm-stop

如果您设置为app.js,则可以使此操作非常简单

process.title = myApp;

然后,在scripts.json中,

"scripts": {
    "start": "app.js"
    , "stop": "pkill --signal SIGINT myApp"
}

就是说,如果这是我,我会使用pm2git push来自动处理此问题。


仍然有错误。显然,我精通行命令。
ngungo 2014年

@ngungo而是--signal。使用man pkill阅读有关pkill的。
埃文·卡罗尔

3
@EvanCarroll如果正在运行多个应用程序实例怎么办?
阿米特·库玛·古普塔

1
任何想法如何在angular 4应用程序中实现这一点。具体在哪里设置流程标题?
kiranghule27

40

此处所有其他解决方案均取决于操作系统。适用于任何操作系统的独立解决方案如下使用socket.io。

package.json 有两个脚本:

"scripts": {
  "start": "node server.js",
  "stop": "node server.stop.js"
}

server.js-您平时表达的东西都住在这里

const express = require('express');
const app = express();
const server = http.createServer(app);
server.listen(80, () => {
  console.log('HTTP server listening on port 80');
});

// Now for the socket.io stuff - NOTE THIS IS A RESTFUL HTTP SERVER
// We are only using socket.io here to respond to the npmStop signal
// To support IPC (Inter Process Communication) AKA RPC (Remote P.C.)

const io = require('socket.io')(server);
io.on('connection', (socketServer) => {
  socketServer.on('npmStop', () => {
    process.exit(0);
  });
});

server.stop.js

const io = require('socket.io-client');
const socketClient = io.connect('http://localhost'); // Specify port if your express server is not using default port 80

socketClient.on('connect', () => {
  socketClient.emit('npmStop');
  setTimeout(() => {
    process.exit(0);
  }, 1000);
});

测试一下

npm start (照常启动服务器)

npm stop (这将停止您正在运行的服务器)

上面的代码尚未经过测试(这是我的代码的简化版本,我的代码确实可以工作),但希望它能按原样工作。无论哪种方式,它都提供了您要使用socket.io停止服务器时要采取的一般方向。


2
这种方法的优点在于,您基本上可以在任何环境(包括容器)上运行该环境,这些环境通常对您处理流程的方式有很大的限制。从我个人的角度来看-这是最优雅的方法。
Der Zinger

16

当我尝试建议的解决方案时,我意识到我的应用程序名称已被截断。我process.title在nodejs文档(https://nodejs.org/docs/latest/api/process.html#process_process_title)上进行了阅读,上面写着

在Linux和OS X上,它被限制为二进制名称的大小加上命令行参数的长度,因为它会覆盖argv内存。

我的应用程序不使用任何参数,因此我可以将这行代码添加到我的 app.js

process.title = process.argv[2];

然后将这几行添加到我的package.json文件中

  "scripts": {
    "start": "node app.js this-name-can-be-as-long-as-it-needs-to-be",
    "stop": "killall -SIGINT this-name-can-be-as-long-as-it-needs-to-be"
  },

使用非常长的进程名称。 npm startnpm stop工作,当然npm stop总会终止所有正在运行的进程,但这对我来说是可以的。


12

这是薄荷版本的问题,也可以使用cmd。要终止服务器进程,只需运行以下命令:

    taskkill -F -IM node.exe

2
杀死main node.exe并不是一个好主意,因为如果您有多个正在运行的节点应用程序,它将造成问题
user889030

11

在MAC OS X(/ BSD)上:您可以尝试使用lsof(列出打开的文件)命令

$ sudo lsof -nPi -sTCP:LISTEN

在此处输入图片说明

所以

$ kill -9 3320

9

使用netstat -nptl检查所有进程

Active Internet connections (only servers)
Proto Recv-Q Send-Q Local Address           Foreign Address         State       PID/Program name
tcp        0      0 127.0.0.1:27017         0.0.0.0:*               LISTEN      1736/mongod     
tcp        0      0 0.0.0.0:22              0.0.0.0:*               LISTEN      1594/sshd       
tcp6       0      0 :::3977                 :::*                    LISTEN      6231/nodejs     
tcp6       0      0 :::22                   :::*                    LISTEN      1594/sshd       
tcp6       0      0 :::3200                 :::*                    LISTEN      5535/nodejs 

而且它只是通过PID引用终止了该进程。...就我而言,我想停止6231 / nodejs,所以我执行以下命令:

kill -9 6231

1
我认为OP正在寻找NPM脚本选项而不是控制台。
法拉吉·安德森

4

这是另一个解决方案,融合了先前答案中的想法。在解决有关平台独立性的问题时,它采用了“杀死进程”方法。

它依靠tree-kill软件包来处理杀死服务器进程树。我发现杀死我的项目中的整个过程树是必要的,因为某些工具(例如babel-node)产生了子过程。如果只需要杀死一个进程,则可以使用内置process.kill()方法替换tree-kill 。

解决方案如下(spawn()应修改前两个参数以反映运行服务器的特定方法):

构建/启动server.js

import { spawn } from 'child_process'
import fs from 'fs'

const child = spawn('node', [
  'dist/server.js'
], {
  detached: true,
  stdio: 'ignore'
})
child.unref()

if (typeof child.pid !== 'undefined') {
  fs.writeFileSync('.server.pid', child.pid, {
    encoding: 'utf8'
  })
}

build / stop-server.js

import fs from 'fs'
import kill from 'tree-kill'

const serverPid = fs.readFileSync('.server.pid', {
  encoding: 'utf8'
})
fs.unlinkSync('.server.pid')

kill(serverPid)

package.json

"scripts": {
  "start": "babel-node build/start-server.js",
  "stop": "babel-node build/stop-server.js"
}

请注意,此解决方案将启动脚本与服务器分离(即,npm start将立即返回并且在服务器停止之前不会阻塞)。如果您喜欢传统的阻止行为,只需删除的options.detached参数spawn()和对的调用child.unref()


3

如果您已经尝试过ctrl + c并且仍然无法使用,则可能需要尝试一下。这对我有用。

  1. 以管理员身份运行命令行。然后运行下面的命令以查找要杀死的processID(PID)。在输入您的端口号<yourPortNumber>

    netstat -ano | findstr :<yourPortNumber>

在此处输入图片说明

  1. 然后,在标识了PID后执行此命令。

    taskkill /PID <typeYourPIDhere> /F

在此处输入图片说明

@mit $ ingh的荣誉来自http://www.callstack.in/tech/blog/windows-kill-process-by-port-number-157


2

如果很简单,那就杀死进程。

localmacpro$ ps
  PID TTY           TIME CMD
 5014 ttys000    0:00.05 -bash
 6906 ttys000    0:00.29 npm   
 6907 ttys000    0:06.39 node /Users/roger_macpro/my-project/node_modules/.bin/webpack-dev-server --inline --progress --config build/webpack.dev.conf.js
 6706 ttys001    0:00.05 -bash
 7157 ttys002    0:00.29 -bash

localmacpro$ kill -9 6907 6906

1

对于Windows机器(我在Windows 10上),如果cli上的CTRL + C(Cancel / Abort)命令不起作用,并且屏幕显示如下:

在此处输入图片说明

尝试先按ENTER键(或按任意键),然后按CTRL + C,当前进程将询问您是否要终止批处理作业:

在此处输入图片说明

也许CTRL + C仅终止父进程,而npm start与其他子进程一起运行。完全不确定为什么您必须在CTRL + C之前就按下该额外的键,但是它比必须关闭命令行然后重新启动要好得多。

您可能要检查的一个相关问题:https : //github.com/mysticatea/npm-run-all/issues/74




0

如果您的json文件没有停止该应用程序的脚本,则我使用的选项只是在cmd上按ctrl + C。


-1

所有(3)排序是:

1- CTLR + C

2-在json文件中写入停止脚本

“ scripts”:{“ stop”:“ killall -SIGINT这个名称可以长期存在,”},

*比命令写入// npm stop //

3-重启电脑


7
重新启动电脑,真的吗?!?为什么不只翻转主断路器?:D
stk

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.