
내 스크립트에는 다음과 같은 매우 간단한 기능이 있습니다.
# Used for debug tracing.
log()
{
:
echo "log: $1"
}
한 곳에서 로깅을 사용자 정의/해제할 수 있다는 아이디어입니다. 매우 조잡합니다.
이제 릴리스 구성 시 스크립트가 전혀 출력을 생성하지 않기를 원합니다. 내가 생각한 유일한 솔루션이지만 매우 건조하지 않습니다.
TMPFILE='/tmp/tempfilewithpossiblyuniquename'
cmd 1>"$TMPFILE" 2>"$TMPFILE"
cat "$TMPFILE" | xargs log
rm "$TMPFILE"
~을 위한모든 명령 하나하나. 이를 개선하는 방법은 무엇입니까?
편집: 수집하고 싶습니다모두로 출력 stdout
하고 stderr
를 통해 채널을 보냅니다 log()
. 그런 다음 log()
모든 것을 무시하고, 파일에 기록하고, 인쇄하는 등을 선택할 수 있습니다.
답변1
첫째, 해당 함수는 전송된 모든 항목의 첫 번째 "단어"만 기록 합니다 $1
."$*"
둘째, 이런 종류의 작업을 수행하는 방법은 (보통 POSIX의 경우처럼) 무수히 많습니다. 나는 아마도 다음과 같이 갈 것입니다 :
log() {
cat - >> "$logfile"
}
do_stuff | log
하지만 다음과 같이 할 수도 있습니다.
(
do_stuff
do_more_stuff
) >> "$logfile"
./thing 1> /dev/null 2> &1
모든 출력을 완전히 억제하는 것은 일반적으로 "코드 내에서" 잠그는 것보다 호출 환경(예: )에 남겨두는 것이 가장 좋습니다 . 그것은 말했다:
squashout="true" # comment this out to stop killing output
if ! [[ "true" = "${squashout-false}" ]]; then
# Redirect stdout and stderr to the null device.
exec 1> /dev/null
exec 2> /dev/null
fi
답변2
절대 간단한 출력은 없습니다. 스크립트를 stdout
다음 stderr
으로 리디렉션하면 됩니다 /dev/null
.
exec >/dev/null 2>&1
이는 셸 자체와 이후에 실행되는 모든 명령에 영향을 미칩니다. 출력이 리디렉션되는 위치를 선택하려면 조건부로 실행하세요.
if [ "$output_to_file" = 1 ]; then
exec > "$outputfilename" 2>&1
elif [ "$output_suppress" = 1 ]; then
exec > /dev/null 2>&1
fi
참고로 억제하는 것은모두출력은 아마도 좋은 생각이 아닐 것입니다. 사용자가 원할 가능성이 매우 높습니다.일부오류에 대한 알림.
함수를 통해 출력을 전달하고 Bash/ksh/Zsh를 실행하는 경우 프로세스 대체를 사용할 수 있습니다.
#!/bin/bash
mangle_output() {
# do something smarter here
while read -r line; do
echo "output: $line";
done;
}
# redirect stdout and stderr to the function
exec > >(mangle_output) 2>&1
echo something that produces output
쉘 루프를 사용하여 출력을 처리하는 것은 그다지 좋은 생각은 아니지만 적어도 속도는 느립니다. 보다:쉘 루프를 사용하여 텍스트를 처리하는 것이 나쁜 습관으로 간주되는 이유는 무엇입니까?. 원하는 것이 파일을 리디렉션하는 것뿐이라면 리디렉션을 설정하는 데 /dev/null
사용하세요 .exec