programing

동일한 로그 파일에 추가되는 표준 및 오류 출력의 리디렉션

newsource 2023. 8. 13. 09:46

동일한 로그 파일에 추가되는 표준 및 오류 출력의 리디렉션

나는 여러 공정의 표준 출력과 오류 로그를 하나의 로그 파일로 수집해야 합니다.

따라서 모든 출력이 이 로그 파일에 추가되어야 합니다.

다음과 같은 행을 가진 모든 작업을 호출합니다.

$p=start-process myjob.bat -redirectstandardoutput $logfile -redirecterroroutput $logfile -wait

첨부할 정보는 어디에 넣어야 합니까?

파일에 추가하려면 약간 다른 방법을 사용해야 합니다.개별 프로세스의 표준 오류 및 표준 출력을 파일로 리디렉션할 수 있지만 파일에 추가하려면 다음 작업 중 하나를 수행해야 합니다.

  1. 에서 생성한 stdout/stderr 파일 내용 읽기Start-Process
  2. 시작 프로세스를 사용하지 않고 통화 연산자를 사용합니다.
  3. Start-Process를 사용하지 않고 를 사용하여 프로세스를 시작합니다.NET 객체

첫 번째 방법은 다음과 같습니다.

$myLog = "C:\File.log"
$stdErrLog = "C:\stderr.log"
$stdOutLog = "C:\stdout.log"
Start-Process -File myjob.bat -RedirectStandardOutput $stdOutLog -RedirectStandardError $stdErrLog -wait
Get-Content $stdErrLog, $stdOutLog | Out-File $myLog -Append

두 번째 방법은 다음과 같습니다.

& myjob.bat 2>&1 >> C:\MyLog.txt

또는 다음과 같습니다.

& myjob.bat 2>&1 | Out-File C:\MyLog.txt -Append

세 번째 방법:

$pinfo = New-Object System.Diagnostics.ProcessStartInfo
$pinfo.FileName = "myjob.bat"
$pinfo.RedirectStandardError = $true
$pinfo.RedirectStandardOutput = $true
$pinfo.UseShellExecute = $false
$pinfo.Arguments = ""
$p = New-Object System.Diagnostics.Process
$p.StartInfo = $pinfo
$p.Start() | Out-Null
$p.WaitForExit()
$output = $p.StandardOutput.ReadToEnd()
$output += $p.StandardError.ReadToEnd()
$output | Out-File $myLog -Append

유닉스 셸과 마찬가지로 PowerShell은 다음을 지원합니다.>다음을 포함하여 Unix에서 알려진 대부분의 변형을 사용하여 리디렉션합니다.2>&1(이상하게도, 순서는 중요하지 않습니다.)2>&1 > file일반적인 것과 똑같이 작동합니다.> file 2>&1).

대부분의 최신 유닉스 셸과 마찬가지로 PowerShell에는 표준 오류와 표준 출력을 모두 동일한 장치로 리디렉션하는 바로 가기가 있습니다. 그러나 유닉스 관례를 따르는 다른 리디렉션 바로 가기와 달리 capture all 바로 가기는 새 서명을 사용하고 다음과 같이 작성됩니다.*>.

따라서 구현 방법은 다음과 같습니다.

& myjob.bat *>> $logfile

앤디는 저에게 좋은 조언을 해주었지만, 저는 훨씬 더 깨끗한 방법으로 하고 싶었습니다.그것은 말할 것도 없습니다.2>&1 >>method PowerShell은 다른 프로세스, 즉 stderr과 stdout 모두 액세스를 위해 파일을 잠그려고 하는 로그 파일에 대해 나에게 불평했습니다.그래서 제가 어떻게 해결했는지는 이렇습니다.

먼저 멋진 파일 이름을 생성해 보겠습니다. 하지만 이것은 단지 현학적인 것을 위한 것입니다.

$name = "sync_common"
$currdate = get-date -f yyyy-MM-dd
$logfile = "c:\scripts\$name\log\$name-$currdate.txt"

그리고 여기서 속임수가 시작됩니다.

start-transcript -append -path $logfile

write-output "starting sync"
robocopy /mir /copyall S:\common \\10.0.0.2\common 2>&1 | Write-Output
some_other.exe /exeparams 2>&1 | Write-Output
...
write-output "ending sync"

stop-transcript

와 함께start-transcript그리고.stop-transcriptPowerShell 명령의 모든 출력을 단일 파일로 리디렉션할 수 있지만 외부 명령에서는 올바르게 작동하지 않습니다.따라서 모든 출력을 PS의 stdout으로 리디렉션하고 나머지는 스크립트가 수행하도록 합니다.

사실, 저는 MS 엔지니어들이 이 문제가 그렇게 간단한 방법으로 해결될 수 있는데 왜 "관련된 높은 비용과 기술적 복잡성 때문에" 아직 해결되지 않았다고 말하는지 모르겠습니다.

쪽이든 모든 을 "" " " " " " 으로 합니다.start-process거대한 잡동사니 IMHO이지만, 이 방법으로, 당신이 해야 할 일은 추가하는 것입니다.2>&1 | Write-Output외부 명령을 실행하는 각 행에 코드를 지정합니다.

아마도 그것은 그렇게 우아하지는 않지만, 다음과 같은 것들도 효과가 있을 것입니다.저는 비동기식으로 이것이 좋은 해결책이 아닐 것이라고 생각합니다.

$p = Start-Process myjob.bat -redirectstandardoutput $logtempfile -redirecterroroutput $logtempfile -wait
add-content $logfile (get-content $logtempfile)

언급URL : https://stackoverflow.com/questions/8925323/redirection-of-standard-and-error-output-appending-to-the-same-log-file