Pra*_*kar 38 command-line bash scripts process
我想检查特定进程是否已经运行。
我参考了这个问答。
但我没有得到任何具体的解决方案。以下是我尝试过的示例:我创建了abc.sh文件并在后台运行此脚本,例如sh abc.sh &.
现在这个文件在后台运行,我启动ps aux | grep "abc"命令。
以下是此命令的输出:
prakash 3594 0.0 0.0 4388 820 pts/0 S+ 16:44 0:00 grep --color=auto abc
Run Code Online (Sandbox Code Playgroud)
之后,我停止abc.sh正在运行的脚本并启动相同的命令ps aux | grep "abc"命令。
但我得到相同的输出,如:
prakash 3594 0.0 0.0 4388 820 pts/0 S+ 16:44 0:00 grep --color=auto abc
Run Code Online (Sandbox Code Playgroud)
有没有其他方法可以找到进程是否正在运行?
job*_*bin 45
每个进程都将在输出中列出ps aux;无论是跑步、睡觉、僵尸还是停止。
但是,在您的情况下,由于您使用 运行该进程sh abc.sh,sh因此是正在运行的应用程序(shell)而不是abc.sh. 因此,ps aux将不包含的过程abc.sh,因为其grep可能不会产生任何结果。
因此,您应该使用它的正确方法是:
ps aux | grep sh
Run Code Online (Sandbox Code Playgroud)
这也可能会返回其他正在运行的进程,sh它们的输出中的任何位置都有字符串ps aux。
您应该注意,当 的输出ps aux具有其STATas时,该进程将“运行” R。如果不是这样,则它不会在您触发命令以检查正在运行的进程的实例上运行。可以在 ps 的手册页中找到不同的进程状态:
D uninterruptible sleep (usually IO)
R running or runnable (on run queue)
S interruptible sleep (waiting for an event to complete)
T stopped, either by a job control signal or because it is being traced
W paging (not valid since the 2.6.xx kernel)
X dead (should never be seen)
Z defunct ("zombie") process, terminated but not reaped by its parent
Run Code Online (Sandbox Code Playgroud)
您也可以运行该top命令来检查进程是否正在运行或睡眠以及它消耗的 CPU 和 RAM 量。(这将再次将您的过程列为sh)。
但是,如果您确实希望将您的进程列为abc.sh,那么您应该将正在运行的脚本的第一行显示为:
#!/bin/sh
Run Code Online (Sandbox Code Playgroud)
以便 shell 知道使用哪个应用程序来运行脚本(在本例中#!/bin/bash为sh,将其更改为 bash),然后使用以下命令为进程提供可执行权限:
chmod +x /path/to/abc.sh
Run Code Online (Sandbox Code Playgroud)
替换/path/to/为abc.sh文件的位置,然后abc.sh使用
/path/to/abc.sh
Run Code Online (Sandbox Code Playgroud)
再次替换/path/to/为abc.sh文件的位置。
我的问题grep是它是一个整行解析器。在您的示例中,您正在搜索“abc”,但它正在拉回grep(正在寻找“abc”)的实例。有点圆。你可以过滤掉它,但我觉得这有点不正常。
我会转向awk一点点华丽。
ps aux | awk '$12=="abc.sh"'
Run Code Online (Sandbox Code Playgroud)
awk根据空格(默认情况下)将行拆分为字段。场$ 11 +是命令列(S),所以如果命令为“sh abc.sh ...”,$11会sh和$12会abc.sh。
如果您想使用 Bash&&和||运算符控制输出或链接,您可以,但您需要更聪明一点。如果没有找到任何东西grep,将退出状态代码 1(技术失败,触发器||),但awk将始终退出代码 0。我们可以通过告诉它在找到某些东西时退出并在没有找到时抛出 1 来改变它:
ps aux | awk '$12=="abc.sh" {exit 0} END{exit 1}' && echo running || echo not running
Run Code Online (Sandbox Code Playgroud)
当然,如果您只关心将输出写入屏幕,则可以全部完成awk:
ps aux | awk '$12=="abc.sh" {print "running"; exit} END{print "not running"}'
Run Code Online (Sandbox Code Playgroud)
检查当前 bash 会话是否在后台启动的进程(如 )的正确方法sh abc.sh &是使用jobs内置命令。
例子:
$ sh abc.sh &
[1] 6917
$ jobs
[1]+ Running sh abc.sh &
Run Code Online (Sandbox Code Playgroud)
这意味着sh abc.sh在后台启动的进程正在运行。如果该过程已完成,您将看到如下内容:
[1]+ Done sh abc.sh
Run Code Online (Sandbox Code Playgroud)
如果您有更多的进程在后台运行,您可以sh abc.sh使用以下命令将输出限制为仅
进程:
jobs sh
Run Code Online (Sandbox Code Playgroud)
查看help jobs更多信息。
上述方法仅在 bash 的当前会话中有效。但是,如果您在另一个 bash 会话中(例如在另一个终端窗口或选项卡中,或在脚本中),除了:
ps aux | grep "[s]h bin/test.sh"
Run Code Online (Sandbox Code Playgroud)
你也可以使用:
pgrep -a sh
Run Code Online (Sandbox Code Playgroud)
这对我来说似乎更简单。如果您将在输出中看到您键入的命令(sh abc.sh在本例中),则表示该进程仍在运行。如果不是,则该过程已完成。