stdin 'hop' over process?

4

Existe uma maneira de o stdin poder 'saltar' sobre um processo? Por exemplo, no seguinte comando,

cat file | ssh host 'mkdir -p /some/directory && cat > /some/directory/file'

Isso enviará o stdin do primeiro cat para mkdir e o segundo cat não receberá stdin. Eu quero que o stdout do primeiro cat pule sobre mkdir e seja enviado apenas para o segundo cat . Estou ciente de que você pode executar algo como:

cat file | ssh host 'cat > /tmp/file2 ; mkdir -p /some/directory && mv /tmp/file2 /some/directory/'

Isso só funciona ao copiar um arquivo ou

cat file | ssh host 'tee >(mkdir -p /some/directory) >/some/directory/file'

Mas isso só funciona porque o comando mkdir não usa stdin. Existe um comando que irá executar um comando que replica essa funcionalidade? Algo como:

cat file | ssh host 'stdinhop mkdir -p /some/directory | cat > /some/directory/file'

onde stdinhop não enviaria seu stdin para mkdir, mas o redireciona para stdout para que o segundo gato possa lê-lo?

    
por stonewareslord 07.03.2015 / 15:28

2 respostas

4

Você pode redirecionar o stdin do primeiro comando de /dev/null :

anthony@Watt:~$ echo -e 'hello\nworld' | ssh localhost 'cat < /dev/null && cat -n'
     1  hello
     2  world

As linhas são numeradas, então o 2 nd cat as obteve.

Se não estiver usando o ssh, você usaria um subshell: echo -e 'hello\nworld' | ( cat < /dev/null && cat -n )

    
por 07.03.2015 / 18:03
2

O que você quer já está acontecendo, na verdade. E certamente mkdir não é problema seu - não lê stdin de qualquer maneira. Esse pipe é herdado como stdin por todos os filhos de ssh - a menos que você esteja recebendo um pseudo terminal como ssh -t .

Salvo isso, o problema é que o shell que executa esses comandos é um dos filhos de ssh - e parte de sua tarefa é abrir 0,1,2 para cada grupo de comando que ele executa. Sua entrada, então, está apenas se perdendo no shuffle porque está em um descritor comum - o mesmo descritor que o shell reabre para cada um de seus filhos.

E, de maneira mais simples, acho que você pode simplesmente mover a entrada para um descritor diferente de um desses três padrões. Por exemplo, o seguinte funciona para mim:

echo hey there >file
cat file | ssh mikeserv@localhost '
               exec 3<&0
               mkdir -p .
               echo ho there
               cat <&3'

Se eu executar o acima, ele imprime:

ho there
hey there

Você também pode encontrar algum utilitário na opção -W para ssh . man ssh diz:

  • -W host : port - Solicita que a entrada e saída padrão no cliente sejam encaminhadas para host na porta sobre o canal seguro. Implica -N , -T , ExitOnForwardFailure e ClearAllForwardings . Funciona apenas com a versão 2 do Protocolo
por 07.03.2015 / 22:51