TL;博士
這將捕獲的stdout輸出,例如從print()
,在文件stdout.txt
和stderr輸出(例如來自未處理的例外),文件stderr.txt
;從PowerShell,使用
cmd /c pythonw myApp.py 1>stdout.txt 2>stderr.txt
)。
注意重定向標準輸出的非常行爲實際上可能再次使你的腳本工作,如果其與pythonw
失敗的唯一原因是利用print
(在Python 2.x的 - 見下文)。
買者:調用*.pyw
腳本時,此輸出重定向技術看似不不工作直接(如通過將腳本文件路徑pythonw.exe
反對)。 如果你知道爲什麼和/或它是否適合你,請告訴我。
發生在要運行與pythonw.exe
任何的Python 2.x或3.x的腳本的頂部以下內容:
import sys, os
if sys.executable.endswith("pythonw.exe"):
sys.stdout = open(os.devnull, "w");
sys.stderr = open(os.path.join(os.getenv("TEMP"), "stderr-"+os.path.basename(sys.argv[0])), "w")
當使用運行腳本時,可以確保以下內容:
print()
調用和顯式調用sys.stdout()
實際上被忽略(不-OPS)。
- Stderr輸出,包括來自未處理的致命異常,發送到文件
%TEMP%\stderr-<scriptFileName>
; %TEMP%
是一個標準的Windows環境變量,指向當前用戶的臨時文件的文件夾。
換句話說:有了上面的代碼,檢查文件%TEMP%\stderr-<scriptFileName>
後當pythonw.exe
調用的腳本已經默默地失敗。
有關解釋,請繼續閱讀。
在Windows上,pythonw.exe
是啓動GUI /無UI不惜一切的腳本,這意味着的 標準輸入和輸出流 - sys.stdin
,sys.stdout
,sys.stderr
不可用。
這有2討厭的副作用:
- 使用
print()
- 它的目標sys.stdout
默認 - 導致在Python 2.x的異常。
- 任何未處理的異常 - 包括在2中由
print()
觸發的一個異常。x - 導致腳本無聲地中止。
- 默認情況下,異常錯誤消息轉到
sys.stderr
,這是此場景中不可用的情況。 - 無論是明確,或隱式地通過print()
上面的代碼通過固定這些問題。
將所有stderr輸出發送到臨時文件。
的Python 2.x和Python 3.x都有差異:
當一個腳本與pythonw.exe
,sys.stdin
,sys.stdout
,並sys.stderr
運行:在Python
- 2.x:有無效 fil Ë描述
- 試圖寫
sys.stdout
或sys.stderr
時最終結果是出現以下異常:IOError: [Errno 9] Bad file descriptor
- 陷阱:由於輸出緩衝,這種異常可能不是表面,直到你輸出,說,4K字節;您可以通過調用
pythonw.exe
和-u
(用於無緩衝輸出)立即激發它。
print()
盲目地嘗試sys.stdout
(默認情況下),所以它遲早會引發這個異常。
- 在Python 3.X:是設置爲
None
- 這是補充與3.X
print()
功能進行無操作(什麼都不做),當它發現sys.stdout
爲None
,所以print()
聲明可以默認安全地使用 - 它們將簡單地被忽略當與pythonw.exe
運行時
- 然而,試圖使用
sys.stdout.write()
和sys.stderr.write()
仍然導致異常。
更多背景信息,請參閱here。
你有沒有解決過這個問題?我用我的劇本面對完全相同的事情。按照Ross的答案寫出stderr/stdout表明腳本*不會啓動,而是在不拋出異常的情況下死亡。 – mfitzp
@mfitzp:您需要將sys.stderr作爲業務的第一順序重定向到文件,否則會丟失未處理異常的錯誤消息;看到我的答案。 – mklement0