double awk comandos no mesmo pipe?

1

Olá, estou tentando fazer algo assim, mas não vai funcionar, vocês podem me dizer que me ajudem?

/usr/bin/mysql -B -r -h ******** -u******* -p****** -D***** \
    -e'SELECT 'username', 'uid', 'gid', 'homedir' FROM 'some_table')' | \
        awk '{print $1":x:"$2":"$3"::"$4":/usr/sbin/nologin"}' >> /tmp/file1 ;
        awk '{print $1":"$5":13753:0:99999:7:::"}'>>/tmp/file2

Alterando ";" para "& &" não funciona também. O arquivo1 e o arquivo2 são criados, mas somente o arquivo1 contém dados. Então basicamente o que eu quero fazer é usar as mesmas variáveis para dois comandos

    
por Apaz 18.10.2011 / 17:20

4 respostas

3

Tente isto:

/usr/bin/mysql -B -r -h ******** -u******* -p****** -D***** \
    -e'SELECT 'username', 'uid', 'gid', 'homedir' FROM 'some_table')' | \
        awk '{ print $1":x:"$2":"$3"::"$4":/usr/sbin/nologin" >> "/tmp/file1"; 
               print $1":"$5":13753:0:99999:7:::" >> "/tmp/file2" }'
    
por 18.10.2011 / 18:07
2

Quando você deseja executar dois comandos diferentes nos mesmos dados do pipe de entrada, é necessário usar um arquivo intermediário:

TMPFILE="$(mktemp)"
/usr/bin/mysql -B -r -h ******** -u******* -p****** -D***** \
               -e'SELECT 'username', 'uid', 'gid', 'homedir' FROM 'some_table')' >"$TMPFILE"
awk '{print $1":x:"$2":"$3"::"$4":/usr/sbin/nologin"}' <"$TMPFILE" >>/tmp/file1
awk '{print $1":"$5":13753:0:99999:7:::"}' <"$TMPFILE" >>/tmp/file2
rm -f "$TMPFILE"

Mas, como o quanta escreve , você pode solicitar única awk instance para fazer as duas operações.

    
por 18.10.2011 / 17:34
1

Você fez uma grande bagunça, começando com a formatação da sua pergunta (veja o que eu fiz acima, o que deve deixar as coisas abaixo mais claras).

Primeiro problema:
  Se você tiver um ponto-e-vírgula ( ; ) ou um "continuar com êxito ( && ), estará executando dois conjuntos separados de comandos.
Completamente separado. É como você correu um, aperte enter e depois correu o outro.
Isso significa que seu segundo awk está procurando stdin por entrada, e não encontrando nada está lhe dando nenhuma saída (é por isso que file2 está vazio)

Segundo problema:
Instâncias separadas de awk não podem compartilhar variáveis. Ou você quer que o segundo awk mastigue a saída da consulta do MySQL, ou você quer que ele mastigue a saída do primeiro awk .
Desde que você tem 5 variáveis em seu segundo awk eu estou assumindo o último.

Solução
Execute a primeira metade da lista de comandos (tudo até o ponto e vírgula).
Agora, execute o segundo awk e especifique um arquivo de entrada ( awk '{print $1":"$5":13753:0:99999:7:::"}' /tmp/file1 >> /tmp/file2 ).

    
por 18.10.2011 / 17:34
0

Seu comando, como mostrado, nunca funcionará, já que o processamento é totalmente sequencial, e a saída do mysql já está esgotada pela primeira instrução awk.

Eu simplesmente movo tudo isso para um pequeno script:

#!/bin/bash
mycmd="SELECT 'username', 'uid', 'gid', 'homedir' FROM 'some_table'"
while read -r username, uid, gid, homedir; do
printf "%s:x:%s:%s::%s:/usr/sbin/nologin" "$username" "$uid" "$gid" "$homedir" >> /tmp/file1
printf "%s:%s:13753:0:99999:7:::" "$username" "missing variable" >>/tmp/file2
done <(/usr/bin/mysql -B -r -h * -u* -p* -D* -e "$mycmd")

Não testado, visite o Wiki do Wooledge para obter mais magia bash do que você sabia que existia:)

    
por 18.10.2011 / 17:43

Tags