TL; DR: >/dev/null 2>&1 || true
silencia efetivamente o comando, descartando qualquer saída (erro ou normal) e o resultado do comando, mas nenhum de seus efeitos colaterais. O que segue é uma explicação do porquê.
Os programas Linux por padrão recebem três descritores de arquivos que são abertos antes que o código principal do programa comece a ser executado. Estes são stdin
(entrada padrão, descritor de arquivo 0), stdout
(saída padrão, descritor de arquivo 1) e stderr
(erro padrão, descritor de arquivo 2). Estes são normalmente ligados ao terminal atual, que hoje significa efetivamente o teclado, a tela e a tela, respectivamente (mas nem sempre foi o caso).
Ao especificar > /dev/null
no comando (o redirecionamento geralmente pode ir a qualquer lugar dentro do comando, mas por convenção ele vai no final ou muito raramente no início), você especifica que a saída padrão ( 1
implícito, mas pode ser especificado usando 1>
em vez de apenas >
) deve ser redirecionado para gravar em /dev/null
, que descarta tudo o que está escrito nele.
2>&1
, em seguida, redireciona o descritor de arquivo 2 ( 2>
) para qual descritor de arquivo 1 está atualmente vinculado a ( &1
).
Um atalho para quando você deseja redirecionar ambos stdout
e stderr
para o mesmo local é usar &>
como em &> /dev/null
. Isso não é suportado em todos os shells, no entanto.
Portanto, especificando > /dev/null 2>&1
, você diz ao sistema que deseja redirecionar a saída padrão do comando para / dev / null e, em seguida, redireciona o erro padrão para a saída padrão (que por sua vez é redirecionada para / dev / null). Isso tem o efeito de silenciar o comando jogando fora toda a sua saída enviada para stdout ou stderr.
Observe que alguns programas usam meios alternativos de desenho na tela, como uma biblioteca terminal como ncurses, e geralmente não serão afetados por isso ou serão afetados de maneiras inesperadas. Mas para programas escritos para serem usados em uma forma de pipe (que inclui a maioria dos programas que geram texto simples para o terminal), isso funciona.
O ||
, por sua vez, significa que se o programa retornar um status de saída diferente de 0 (onde por convenção 0 significa execução bem-sucedida), o shell invocará o comando do outro lado do o ||
, que nesse caso é true
. Não confunda isso com o pipe comum, que usa um único |
e liga o stdout do lado esquerdo ao stdin do lado direito. O oposto de ||
é &&
que executa o lado direito apenas se o lado esquerdo retornou um status de saída igual a 0, e um complementar é ;
, que simplesmente separa vários comandos (o segundo comando será executado independentemente do status de saída do primeiro comando).
true
, por sua vez, é um programa muito simples que tem como único propósito sair com um status de sucesso. Geralmente não é muito útil por si só, mas pode ser muito útil, por exemplo, ao escrever condicionais em scripts de shell. Seu oposto é false
, que sai com um status de falha (diferente de zero), mas por outro lado, como o verdadeiro, não faz nada.
Então, anexando || true
após um comando, você sabe que de qualquer forma, algo será executado com sucesso no momento em que o conjunto de comandos terminar de ser executado. Assim, você sabe que o código de status atual (disponível em $?
) sempre indicará uma execução bem-sucedida.