Linux 管道中的命令失败,未触发;捕获;命令

Linux 管道中的命令失败,未触发;捕获;命令,linux,bash,pipe,conditional-execution,Linux,Bash,Pipe,Conditional Execution,我试图设置一小段代码,这样,如果其中任何一段失败,它都会触发另一行代码运行。就像: cmd1 | | cmd2 但是,第一个管段中有一个管道,因此: cmd1 | cmd2 | cmd3 但是,如果cmd1失败,cmd3不会运行 如果您尝试了以下操作,每次都会得到相同的结果: (cmd1 | cmd2)| cmd3 {cmd1 | cmd2}{cmd3} 为了完整起见,这是我正在使用的特定代码块: { { pkexec apt-y安装(包文件名)| zenity--进度--脉动--自动关闭

我试图设置一小段代码,这样,如果其中任何一段失败,它都会触发另一行代码运行。就像:

cmd1 | | cmd2
但是,第一个管段中有一个管道,因此:

cmd1 | cmd2 | cmd3
但是,如果
cmd1
失败,
cmd3
不会运行

如果您尝试了以下操作,每次都会得到相同的结果:

(cmd1 | cmd2)| cmd3
{cmd1 | cmd2}{cmd3}
为了完整起见,这是我正在使用的特定代码块:

{
{
pkexec apt-y安装(包文件名)| zenity--进度--脉动--自动关闭--无取消--text=“安装(包名称)…。”
} && {
通知发送“(程序包名称)已安装”
}
} || {
zenity--error--text=“错误代码:$?”
}
到目前为止,它的运行就好像“catch”语句(如果您想这样称呼它)根本不存在一样。另外,它的第一部分,特别是在管道之前,是如果失败,它不会抛出错误的部分。我对管道的第二部分没有任何问题,因此我不确定它是否会表现出相同的行为

提前谢谢

( cmd1 | cmd2 ; exit ${PIPESTATUS[0]}) || cmd3

如果在子shell中运行这些命令没有问题,那么这应该适用于您,即
()

您可以使用进程替换来使
zenity
的退出状态不相关

if pkexec apt -y install (package-file-name) > >(
     zenity --progress --pulsate --auto-close --no-cancel --text="installing (package-name) . . ."
   ); then 
    notify-send "(package-name) has been installed"
else
    zenity --error --text="Error code: $?"
fi
或者,您可以使用显式命名管道,以避免需要任何非标准shell扩展

mkfifo p
zenity --progress --pulsate --auto-close --no-cancel --text="installing (package-name) . . ." < p &

if pkexec apt -y install package-file-name > p; then
    notify-send "(package-name) has been installed"
else
    zenity --error --text="Error code: $?"
fi
mkfifop
zenity--进度--脉动--自动关闭--不取消--text=“安装(包名)…”p;然后
通知发送“(程序包名称)已安装”
其他的
zenity--error--text=“错误代码:$?”
fi

在bash中,您可以设置
pipefail
。例如:

$ cat a.sh
#!/bin/bash

false | true || echo executed 1
set -o pipefail
false | true || echo executed 2
$ ./a.sh
executed 2

不相关,但不要使用
。&&…| |
作为三元条件运算符;如果
a
b
失败,
a和&b|c
将运行
c
。改用适当的
if
语句。