Como posso salvar o comando e sua saída de execução no arquivo ao mesmo tempo

1

Suponha que eu tenha um comando java -cp src/ nlp.lm.BigramModel wsj/ 0.1 , quero salvar o próprio comando e a saída de execução do comando no arquivo ao mesmo tempo.

Uma maneira de fazer isso é

echo "$ java -cp src/ nlp.lm.BigramModel atis/ 0.1" > trace/bigram-trace.txt    
java -cp src/ nlp.lm.BigramModel atis/ 0.1 >> trace/bigram-trace.txt

Existe uma maneira melhor de fazer isso?

    
por zack 19.02.2018 / 01:05

4 respostas

2

Você pode fazer algo assim:

echo date | script -q bigram-trace.txt

Resultado:

$ cat bigram-trace.txt
date
sh-4.4$ date
Sun, Feb 18, 2018  6:22:13 PM
sh-4.4$ exit

Ou sem um pipe:

script -q bigram-trace.txt <<'eof'
date
eof
    
por 19.02.2018 / 01:18
0

Eu faria um roteiro para algo que faço com frequência.

cat > foo
#! /bin/bash
echo "\$ $1" > "$2"
$1 >> "$2"
^D
chmod +x foo

e, em seguida, execute

./foo "java -cp src/ nlp.lm.BigramModel atis/ 0.1" "trace/bigram-trace.txt"
    
por 19.02.2018 / 01:13
0

Um método simples e conveniente, especialmente se você quiser salvar não apenas um comando, mas vários, é primeiro executar o comando script e, em seguida, executar seus comandos. script salva a entrada e a saída em todos os comandos. Quando terminar, digite exit ou ctrl-D para sair de script .

Por exemplo, para gravar entrada e saída para dois comandos:

$ script
Script started, file is typescript
$ date
Sun Feb 18 16:59:45 PST 2018
$ for i in {1..3}; do echo $((i**2)); done
1
4
9
$ exit
Script done, file is typescript

Para ver as informações salvas, cat o arquivo typescript :

$ cat typescript
Script started on Sun 18 Feb 2018 04:59:37 PM PST
$ date
Sun Feb 18 16:59:45 PST 2018
$ for i in {1..3}; do echo $((i**2)); done
1
4
9
$ exit

Script done on Sun 18 Feb 2018 05:00:13 PM PST

script tem muitas opções. Veja man script para detalhes.

    
por 19.02.2018 / 02:04
0
( exec >logfile 2>&1; set -x; somecommand )

ou apenas

( set -x; somecommand ) >logfile 2>&1

Isso ativaria o rastreio no subshell (...) e redirecionaria toda a saída para o arquivo logfile .

Se somecommand for mount , o arquivo logfile poderá acabar parecendo

+ mount
/dev/sd0a on / type ffs (local)
/dev/sd0d on /tmp type ffs (local, nodev, nosuid, softdep)
/dev/sd0e on /var type ffs (local, nodev, nosuid)
/dev/sd0f on /usr type ffs (local, nodev)
/dev/sd0g on /usr/local type ffs (local, nodev, wxallowed)
/dev/sd0h on /home type ffs (local, nodev, nosuid, wxallowed, softdep)
/dev/sd0j on /backup type ffs (local, nodev, nosuid)
/dev/sd0k on /extra type ffs (local, nodev, nosuid, wxallowed, softdep)
mfs:92196 on /tmp_mfs type mfs (asynchronous, local, nodev, nosuid, wxallowed, size=8388608 512-blocks)

O +␣ (um sinal de mais e um espaço) na frente do comando é o prompt de rastreamento ou o prompt quaternário, que pode ser alterado definindo PS4 como uma string de prompt:

( PS4='$ '; set -x; df /tmp ) >logfile 2>&1

O texto acima pode produzir algo como

$ df /tmp
Filesystem  512-blocks      Used     Avail Capacity  Mounted on
/dev/sd0d     10315164       160   9799248     0%    /tmp

em logfile .

Isso funciona bem para comandos simples, que podem ser tudo o que você precisa. Para comandos compostos, as outras respostas que usam script ou utilitários semelhantes podem ser mais adequadas, pois o rastreio do shell de comandos compostos não aparece como se pudesse digitá-los. Também variáveis, etc., serão expandidas na saída de rastreio.

    
por 22.02.2018 / 21:03

Tags