【问题标题】:How to get PID from remote executed command?如何从远程执行的命令中获取 PID?
【发布时间】:2014-08-03 22:29:41
【问题描述】:

如果我在 Bash 中执行以下操作,那么我会得到远程启动的 mbuffer 的 PID,即使 mbuffer 仍在运行,我也会恢复终端,这就是我想要的。

read -r pid < <(ssh 10.10.10.47 'nohup /opt/omni/bin/mbuffer -4 -s 128k -m 2G -v 0 -q -I 8023 >/tmp/mtest </dev/null 2>/tmp/mtest.err & echo $!')

echo $pid

现在我想在 Perl 中做同样的事情,所以我尝试

use Capture::Tiny 'capture';

my ($stdout, $stderr, $exit) = capture {
    system("read -r pid < <(ssh 10.10.10.47 'nohup /opt/omni/bin/mbuffer -4 -s 128k -m 2G -v 0 -q -I 8023 >/tmp/mtest </dev/null 2>/tmp/mtest.err & echo $!'); echo \$pid");
};

print "stdout $stdout\n";
print "stderr $stderr\n";
print "exit   $exit\n";

在这里,我原以为 $stdout 会从最后一个 echo 命令中给我 PID,但我什么也没得到。

问题

如何在 Perl 中获取远程执行的mbuffer 的 PID,这样 Perl 脚本不会等待mbuffer 退出然后继续?

【问题讨论】:

  • 我建议您的系统命令不要使用双引号,而是使用带有替代分隔符的单引号,例如 q{}。您逃脱了\$pid,但未能逃脱$!。因此,可能会报告错误但未向您显示。
  • 非常漂亮的发现。我不能让q{}system() 中工作。它被忽略它接缝。
  • 怎么会有人不喜欢这个问题。 +1 ;)

标签: linux bash perl ssh


【解决方案1】:

问题接缝是不可能在一个system() 中执行两个命令,或者可能是,但无法从最后一个命令获得输出。

创建一个本地 helper 脚本解决了这个问题。

#!/usr/bin/bash

# Redirection of stdin and stderr to files (preventing them from holding
# handles that connect, eventually, to the terminal).

read -r pid < <(ssh $1 "/usr/gnu/bin/nohup /opt/omni/bin/mbuffer -4 -s 128k -m 2G -v 0 -q -I 8023 >/tmp/mtest$2 </dev/null 2>/tmp/mtest.err & echo \$!")

echo $pid

在 Perl 中

my ($stdout, $stderr, $exit) = capture {
     system("/comp/mbuffer-zfs-listen.sh 10.10.10.47 11");
};

【讨论】:

  • 无论如何,您的解决方案是更好的解决方案,因为system() 使用/bin/sh 而不是/bin/bash,您的某些命令功能(如进程替换)可能无法正常工作。更改 env 的值。变量 SHELL/bin/sh 也无济于事。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2011-05-19
  • 1970-01-01
  • 2018-01-17
  • 2018-07-28
  • 2020-02-11
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多