2017-08-12 28 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を参照してください。 echocmd.exe組み込みであるため、

動作しませんWin32::Processにコマンドラインとして"echo hello from process"を渡す理由があります。あなたは、以下のように代わりに、コマンドライン'cmd /c "echo hello from process"'を使用する必要があります。output.txt

#!/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; 

内容:

$ 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

関連する問題