sh [중복]에 'exec &> >(tee -a "$LOG_FILE")'을 적용합니다.

sh [중복]에 'exec &> >(tee -a "$LOG_FILE")'을 적용합니다.

이것에서 bash:

exec &> >(tee -a "$LOG_FILE")

로깅(쓰기)하는 동안 출력이 터미널에 표시되도록 & stderr를 리디렉션 하지만 프로세스 대체를 사용합니다.stdouttee$LOG_FILEsh

sh를 사용하여 스크립트를 실행하면:

sh script

나는 얻다:

syntax error near unexpected token `>'

동일한 결과를 얻으려면 다음을 sh시도했습니다.

exec 2>&1 | tee -a "$LOG_FILE"

그러나 나는 아무 것도 쓰여 있지 않다는 것을 알았고 $LOG_FILE대신 다음을 사용해야 했습니다.

exec > "$LOG_FILE" 2>&1

그러면 로그가 파일에 기록되지만 스크립트를 실행할 때 출력이 표시되지 않습니다.

어떤 아이디어가 있나요?

허용되는 답변에서 다음을 사용하십시오.

mkfifo "$HOME/.pipe.$$"

인라인 코드는 허용되지만 블록 내부에서는 허용되지 않으므로 제안된 답변에 대한 도움말/추가

답변1

여기요

#!/bin/sh
#
LOG_FILE=/tmp/log_file    # Demonstration target

# Set up the redirection to `tee`
mkfifo "$HOME/.pipe.$$"
tee -a "$LOG_FILE" <"$HOME/.pipe.$$" &
exec 1>"$HOME/.pipe.$$" 2>&1
rm -f "$HOME/.pipe.$$"

# Using the redirection
echo hello
date
echo STDERR >&2

exit 0

변환의 핵심은 파이프라인 생성, 리디렉션 생성을 중심으로 이루어집니다.표준 입력for tee및 리디렉션표준 출력그리고표준 에러나머지 과정을 위해. 중간에는 tee자신에 대한 호출이 있습니다.

tee -a "$LOG_FILE" <"$HOME/.pipe.$$" &

여기에서는 "$LOG_FILE"방금 생성한 파이프를 읽어서 작성(추가)하고 &평소와 같이 백그라운드에서 실행되는 명령을 추적합니다. 파이프가 양쪽(작성기와 판독기)에서 열리면 파일 시스템에서 삭제할 수 있습니다. 파이프는 여전히 존재하고 양쪽에서 완료될 때까지 사용할 수 있지만 더 이상 이름으로 액세스할 수 없습니다.

안에초기 편집이 스크립트에서는 스크립트 끝에서 종료할 준비를 하기 위해 명령의 PID를 tee변수에 캡처합니다. 그러나 누군가가 나에게 스크립트 끝에서 프로세스를 종료할 $tpid필요가 없다는 점을 올바르게 지적했습니다 . 작성자가 마침내 파이프를 닫으면 어쨌든 치명적이 되기 때문입니다.teeSIGPIPE

$LOG_FILE프로덕션 코드에서는 안전한 장소에서 작성 한다고 가정합니다 . /tmp나머지 코드가 작동할 수 있도록 자리 표시자로 넣었습니다 .

답변2

그냥 해:

#! /bin/sh -
LOG_FILE=/var/log/myscript.log
{
  the whole script here:
  ...
} 2>&1 | tee -a -- "$LOGFILE"

또는:

#! /bin/sh -
LOG_FILE=/var/log/myscript.log
main() {
  the whole script here:
  ...
}
main "$@" 2>&1 | tee -a -- "$LOGFILE"

스크립트 종료 상태는 tee's입니다. 이는 옵션을 사용하여 해결할 수 있지만 이 옵션이 표준의 다음 버전에서 표준이 되더라도 pipefail여전히 이를 지원하지 않는 일부 구현이 있습니다(가장 두드러짐). 바라보다shshdashkorn 쉘에서 반품 상태를 캡처하고 동시에 tee를 사용하는 방법은 무엇입니까?다른 방법의 경우.

sh1980년대에는 일반적으로 Bourne 쉘(Thompson 쉘을 상속함)이었지만 오늘날에는 ksh88 (Bourne 쉘의 파생물)의 하위 집합을 기반으로 하는 표준 POSIX 언어용 인터프리터의 하나 또는 다른 구현 sh입니다 . sh, Bourne 쉘이 아닌. 프로세스 교체는 ksh(원래 ksh86)에서 이루어지지만 POSIX는 아직 이를 지정하지 않았 sh으며 Almquist 쉘(원래 Bourne 쉘의 복제본) 또는 Forsyth 쉘(원래는 Bourne 쉘의 복제본이지만 pdksh/mksh 포함)에서 파생됩니다. Korn 쉘). .ksh88 을 지원하지 않는 시스템에서도 사용할 수 없습니다 /dev/fd/n.

관련 정보