Tenho um longo pipeline de comandos no zsh
script:
pv /dev/sda > sda.raw | sha256sum > sda.raw.sha256 | cut -c61-64 | read SHASUM
como posso verificar dentro de uma if
instrução se todos os comandos foram encerrados com sucesso?
Eu sei ${pipestatus[@]}
, mas é uma matriz. Então eu teria que verificar cada elemento individualmente.
Existe algum atalho para verificar se ${pipestatus[@]}
contém apenas 0
?
ATUALIZAR:
Eu descobri um comportamento estranho:
para testes, configurei um pequeno sistema de arquivos (10 MB) para que ele seja preenchido rapidamente:
#!/bin/zsh
set -o pipefail
if pv /dev/zero > loop/file ; then
echo OK
else
echo FAIL
fi
como esperado, recebo o seguinte erro e "FAIL" é impresso:
pv: write failed: No space left on device
No entanto, quando altero um pouco o comando pv, de repente ele não imprime nenhum erro e o comando pv parece ser executado indefinidamente (mesmo que não haja mais espaço no dispositivo)
#!/bin/zsh
set -o pipefail
if pv /dev/zero > loop/file | sha256sum ; then
echo OK
else
echo FAIL
fi
Duas opções:
definir a
pipefail
opção de ksh (set -o pipefail
), então o status de saída de um pipeline será o do componente do pipeline mais à direita que falhou.procure valores diferentes de zero em
$pipestatus
. Com aextendedglob
opção habilitada$pipestatus[(r)^0]
(ou$pipestatus[(r)<1->]
que não requerextendedglob
) retornará o status de saída do componente do pipeline com falha mais à esquerda e$pipestatus[(R)^0]
do mais à direita, para que você possa fazer:ou
Com o
I
sinalizador de subscrito em vez der
/R
, você obterá oI
índice do elemento correspondente mais à direita, para poder fazer:${pipestatus:#0}
irá se expandir para os componentes$pipestatus
exceto 0, então você também pode fazer: