Perl 스크립트에서 시스템 명령의 stdin 및 stdout을 어떻게 캡처할 수 있습니까?

StackOverflow https://stackoverflow.com/questions/78091

  •  09-06-2019
  •  | 
  •  

문제

Perl 스크립트 중간에 실행하려는 시스템 명령이 있습니다.stdin에 입력해야 하는 데이터가 포함된 문자열이 있고(명령은 stdin의 입력만 허용) stdout에 기록된 출력을 캡처해야 합니다.나는 Perl에서 시스템 명령을 실행하는 다양한 방법을 살펴보았습니다. open 기능은 내가 필요한 것 같습니다. 단, stdin 또는 stdout 중 하나만 캡처할 수 있고 둘 다 캡처할 수는 없는 것 같습니다.

현재 가장 좋은 해결책은 다음을 사용하는 것 같습니다. open, stdout을 임시 파일로 리디렉션하고 명령이 완료된 후 파일에서 읽습니다.더 나은 해결책이 있습니까?

도움이 되었습니까?

해결책

제 생각에는 당신이 살펴보고 싶은 것 같아요 IPC::오픈2

다른 팁

IPC::Open2/3은 괜찮지만 일반적으로 나에게 꼭 필요한 것은 IPC::런3, 최소한의 복잡성으로 간단한 사례를 정말 잘 처리합니다.

use IPC::Run3;    # Exports run3() by default

run3( \@cmd, \$in, \$out, \$err );

문서에서는 IPC::Run3을 다른 대안과 비교합니다.사용하기로 결정하지 않더라도 읽어 볼 가치가 있습니다.

그만큼 Perlipc 문서 IPC::Open2 및 IPC::Open3을 포함하여 이를 수행할 수 있는 다양한 방법을 다룹니다.

스크립트 상단 어딘가에 다음 줄을 포함하십시오.

use IPC::Open2;

여기에는 일반적으로 기본적으로 대부분의 Perl 배포판과 함께 설치되는 필수 모듈이 포함됩니다.(없는 경우 CPAN을 사용하여 설치할 수 있습니다.) 그런 다음 열기 대신 다음을 호출하십시오.

$pid = open2($cmd_out, $cmd_in, 'some cmd and args');

데이터를 $cmd_in으로 보내 명령에 데이터를 보낸 다음 $cmd_out에서 읽어 명령의 출력을 읽을 수 있습니다.

명령의 stderr 스트림도 읽을 수 있도록 하려면 대신 IPC::Open3 모듈을 사용할 수 있습니다.

IPC::Open3은 아마도 당신이 원하는 것을 할 것입니다.STDERR 및 STDOUT을 캡처할 수 있습니다.

http://metacpan.org/pod/IPC::Open3

제가 최근에 발견한 아주 쉬운 방법은 다음과 같습니다. 그만큼 IPC::필터 기준 치수.이를 통해 작업을 매우 직관적으로 수행할 수 있습니다.

$output = filter $input, 'somecmd', '--with', 'various=args', '--etc';

목록을 전달하면 셸을 거치지 않고 명령을 호출하는 방법에 유의하세요.또한 일반적인 유틸리티에 대한 오류를 처리하는 합리적인 작업도 수행합니다.(실패하면 dies, STDERR의 텍스트를 오류 메시지로 사용합니다.성공하면 STDERR이 삭제됩니다.)

물론 스트리밍 처리를 수행할 수 있는 방법이 없기 때문에 엄청난 양의 데이터에는 적합하지 않습니다.또한 오류 처리가 요구 사항에 비해 충분히 세부적이지 않을 수도 있습니다.하지만 이는 많은 간단한 사례를 실제로 정말 단순한.

특별한 Perl 명령이 있습니다

open2()

자세한 내용은 다음에서 확인할 수 있습니다. http://sunsite.ualberta.ca/Documentation/Misc/perl-5.6.1/lib/IPC/Open2.html

추가 패키지를 포함하지 않으려면 다음을 수행하면 됩니다.

open(TMP,">tmpfile");
print TMP  $tmpdata ;
open(RES,"$yourcommand|");
$res = "" ;
while(<RES>){
$res .= $_ ;
}

이는 귀하가 제안한 것과 반대이지만 작동해야 합니다.

한 줄의 출력만 기대하거나 개행 문자가 아닌 다른 것으로 결과를 분할하려는 경우 항상 이 방법을 사용합니다.

my $result = qx( command args 2>&1 );  
my $rc=$?;  
# $rc >> 8 is the exit code of the called program.

if ($rc != 0 ) {  
    error();  
}  

여러 줄의 응답을 처리하려면 결과를 배열로 가져옵니다.

my @lines = qx( command args 2>&1 );  

foreach ( my $line ) (@lines) {  
    if ( $line =~ /some pattern/ ) {  
        do_something();  
    }  
}  
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top