在 Perl 中打开管道是不是涉及 shell?

Posted

技术标签:

【中文标题】在 Perl 中打开管道是不是涉及 shell?【英文标题】:Does opening a pipeline in Perl involve a shell?在 Perl 中打开管道是否涉及 shell? 【发布时间】:2020-04-20 06:37:09 【问题描述】:

如果我在 Unix/Linux 系统上的 Perl 脚本中执行此操作:

open(my $fh, 'cat|');

是否涉及到外壳?如果没有,那该怎么办:

open(my $fh, 'cat -v|');

如果可能的话,我想避免使用 shell,我什至知道该怎么做:

open(my $fh, '-|') || exec('cat', '-v');

但简洁也很有价值。

【问题讨论】:

【参考方案1】:

来自open,以下代码示例

每个块中的最后两个示例将管道显示为“列表形式”,但并非所有平台都支持。一个好的经验法则是,如果你的平台有一个真正的 fork(换句话说,如果你的平台是 Unix,包括 Linux 和 MacOS X),你可以使用列表形式。 您可能希望使用管道的列表形式,这样您就可以将文字参数传递给命令,而不会有 shell 解释其中的任何 shell 元字符的风险。 但是,这也会阻止您打开命令的管道故意包含 shell 元字符,[...]

(我的重点)

前面的最后一个例子是

open(my $fh, "-|", "cat", "-n", $file);

顺便说一句,这几乎正是您在问题中的示例。

所以使用“列表形式”,没有外壳。这也适用于system(但是,唉,不适用于qx)

【讨论】:

Re "但是,唉,不适用于qx",参见核心模块 IPC::System::Simple 中的capturex IPC::System::Simple 不是核心,但IPC::ReadpipeX 的文档显示了一种在绕过外壳时模拟 qx/readpipe 的核心方法(剧透,与此答案非常相似) .

以上是关于在 Perl 中打开管道是不是涉及 shell?的主要内容,如果未能解决你的问题,请参考以下文章

在 perl 中打开一个管道进程(sqlplus)并从查询中获取信息?

Perl模块推荐23——Perl::Shell

序言:我为什么学Perl

Perl:关闭信号处理程序中的子进程管道挂起?

如何使用 Python 将标准输入/标准输出通过管道传输到 Perl 脚本

Perl:当子/管道的文件句柄被别名时,关闭子进程失败