Mam skrypt bash z dużą ilością danych wyjściowych i chciałbym zmienić ten skrypt (nie tworzyć nowego), aby skopiować wszystkie dane wyjściowe do pliku, tak jak by to było, gdybym przepuszczał go przez tee.
Mam plik script.sh :
#!/bin/bash
init
do_something_that_outputs_stuff_to_STDOUT
launch_applications_that_output_to_STDOUT
fini
i chciałbym zrobić kopię STDOUT do pliku script.log bez konieczności pisania za ./script.sh | tee script.log
każdym razem.
Dzięki, Tom
Odpowiedzi:
Nie mogłem zmusić do działania bardzo prostego liniowca Dennisa, więc oto o wiele bardziej skomplikowana metoda. Spróbuję jego pierwszego.
Jak wspomniano, możesz użyć exec do przekierowania standardowego błędu i standardowego wyjścia dla całego skryptu. W ten sposób:
exec > $LOGFILE 2>&1
Spowoduje to wyświetlenie wszystkich stderr i stdout do $ LOGFILE.Teraz, ponieważ chcesz wyświetlać to na konsoli, a także plik dziennika, będziesz musiał także użyć nazwanego potoku dla exec do pisania i tee do odczytu.
(One-liner Dennisa technicznie też to robi, choć oczywiście w inny sposób). Za pomocą tej rury jest tworzona
mkfifo $PIPEFILE
. Następnie wykonaj następujące czynności.Jeśli chcesz być dokładny, możesz utworzyć i zniszczyć nazwany plik potoku na początku i na końcu skryptu.
Dla przypomnienia, większość tego zebrałem z bardzo pouczającego posta na blogu przypadkowego faceta: ( Wersja zarchiwizowana )
źródło
Po prostu dodaj to na początku skryptu:
To doda wszystkie dane wyjściowe wysłane do standardowego pliku
script.log
, pozostawiając poprzednią zawartość na miejscu. Jeśli chcesz zacząć od nowa za każdym razem, gdy skrypt jest uruchamiany, po prostu dodajrm script.log
bezpośrednio przed tymexec
poleceniem lub usuń je-a
ztee
polecenia.Ta
-i
opcja powodujetee
ignorowanie sygnałów przerwania i może pozwolićtee
na złapanie pełniejszego zestawu wyjściowego.Dodaj ten wiersz, aby złapać wszystkie błędy (w osobnym pliku):
>
Ważne są odstępy między wieloma symbolami.źródło
To jest połączona wersja odpowiedzi opublikowanej wcześniej przez Dennisa Williamsona. Dołącza zarówno err i std out do script.log we właściwej kolejności.
Dodaj tę linię na początku skryptu:
Zwróć uwagę na odstęp między
>
znakami. Działa dla mnie na GNU bash, wersja 3.2.25 (1) -release (x86_64-redhat-linux-gnu)źródło
Przypuszczam, że inne podejście jest takie:
źródło
Jeśli chcesz kopię wyniku, możesz użyć
tee
tego sposobu:Spowoduje to jednak zalogowanie tylko stdout do script.log. Jeśli chcesz się upewnić, że stderr i stdout są przekierowane, użyj:
Możesz nawet uczynić to nieco ładniejszym dzięki małej funkcji:
źródło
2>&1
i po prostu wyrzuciłbym to do tee.Po prostu użyjesz tego:
Wyprowadza to wszystko do tego dziennika, wszystko, a także wyświetla na ekranie. Jeśli chcesz uzyskać pełny wynik, oto jak to zrobić.
Jeśli jesteś leniwy, możesz ponownie odtworzyć skrypt.
źródło
script
jest to pakiet, np.sudo apt-get install script
aby go zainstalować na Debianie aromatyzowane ,script -ac 'command opts' ~/Documents/some_log.script
można dodatkowo sprawdzić go w terminalu za pomocą czegoś takiegostrings ~/Documents/some_log.script | more
;strings
być prostym sposobem wstępnej dezynfekcji niektórych rzeczy, którescript
wstrzykuje, aby umożliwić bardziej wyszukane metody ponownego odtwarzania / przeglądania. W przeciwnym razie solidna odpowiedź @ Phishy, ponieważscript
również zachowuje interaktywne rzeczy.Możesz dowiedzieć się więcej o tym, jak to działa tutaj: http://www.xaprb.com/blog/2006/06/06/what-does-devnull-21-mean/
źródło
tee
.