2017-08-12 163 views
1

我在使用Win32 :: Process的Perl腳本中運行一個命令,並且我需要將該命令的輸出重定向到一個文本文件。在做了一些研究後,這就是我正在嘗試的:如何將Win32 :: Process命令的輸出重定向到文本文件?

use Win32::Process; 

open (OLDOUT, ">&STDOUT"); 
open (OLDERR, ">&STDERR"); 
my $file = "output.txt"; 
open (STDOUT, ">$file"); 
open (STDERR, ">&STDOUT"); 

my $timeout = 1000 * 60; # 60 second timeout 
my $proc; 
my $exit; 
my $exe = "C:/Windows/System32/cmd.exe"; 
Win32::Process::Create($proc, $exe, "echo hello from process", 1, DETACHED_PROCESS, "."); 
$proc->Wait($timeout); 
$proc->GetExitCode($exit); 

system("echo hello from system"); # To verify that the redirect is working 

close (STDOUT); 
close (STDERR); 
open (STDOUT, ">&OLDOUT"); 
open (STDERR, ">&OLDERR"); 
close (OLDOUT); 
close (OLDERR); 

不幸的是,這是行不通的。在output.txt文件中,我只收到「hello from system」。有沒有辦法用Win32 :: Process完成我想要的功能?

我使用Win32 :: Process而不是反引號的原因是因爲我的命令有時會崩潰,並且我需要提供超時以便在必要時終止它。 Win32 :: Process的 - > Wait()函數允許我這樣做。

我寧願有一個使用Win32 :: Process的解決方案,因爲我受限於我有權訪問哪些模塊。但是,如果真的不能這樣做,我會歡迎使用其他模塊的示例解決方案。

謝謝。

回答

1

在開始進程時指定DETACHED_PROCESS。這樣做的效果是:

DETACHED_PROCESS0x00000008

對於控制檯程序,新的進程不會繼承其父的控制檯(默認值)。

參見Process Creation Flags

原因傳遞"echo hello from process"作爲命令行Win32::Process不起作用是因爲echocmd.exe內置。你需要,而不是使用命令行'cmd /c "echo hello from process"',如下圖所示:

#!/usr/bin/env perl 

use strict; 
use warnings; 

use File::Which qw(which); 
use Win32; 
use Win32::Process; 

open OLDOUT, ">&STDOUT"; 
open OLDERR, ">&STDERR"; 

my $file = 'output.txt'; 

open STDOUT, ">$file"; 
open STDERR, ">&STDOUT"; 

my $timeout = 15 * 1_000; 
my ($proc, $exit); 
my $exe = which 'cmd.exe'; 
Win32::Process::Create($proc, $exe, 'cmd /c "echo hello from spawned process"', 1, 0, '.'); 
$proc->Wait($timeout); 
$proc->GetExitCode($exit); 

print "Doing work ...\n"; sleep 3; 

print "Spawned process exited with $exit\n"; 

close STDERR; 
close STDOUT; 
open STDERR, ">&OLDERR"; 
open STDOUT, ">&OLDOUT"; 
close OLDERR; 
close OLDOUT; 

內容的output.txt

$ perl main.pl 

$ type output.txt 
hello from spawned process 
Doing work ... 
Spawned process exited with 0 
+0

謝謝您的解決方案。我已經用$ exe = which'gnatmake'來測試它,命令被替換爲「gnatmake -v」,並且輸出被正確寫入output.txt。我也刪除了分叉進程,因爲我相信這是不必要的。看起來我的真正問題是使用echo命令,因爲我仍然無法使用它。但是因爲我只是用它來測試,所以我不在乎。 – epsilonjon

+0

我已經測試過這個,它工作完美。感謝您的幫助。 – epsilonjon

相關問題