2011-11-27 2 views
3

gpg.exe --passphrase-file my.passphrase --decrypt --output MTR241_20111124.htm MTR241_20111124.htm.gpg (--batch 및 --yes 옵션 없음)을 사용하여 해독하려고합니다. 누군가가 gpg.exe --passphrase-file ..\BE\src\my.passphrase --symmetric --output MTR241_20111124.htm.gpg MTR241_20111124.htm을 테스트하는 데 신경 쓰면 암호화 명령도 제공합니다.Java 프로세스가 gpg.exe의 InputStream, OutputStream을 캡처 할 수 없습니다.

두 가지 경우가 있습니다. 사례 1 : MTR241_20111124.htm 파일이 출력 디렉터리에 없습니다. 명령 프롬프트와 캡쳐 된 exec 스트림 모두 동일한 출력을 제공합니다.

C:\Eclipse\workspace2\sync_inbox>gpg.exe --passphrase-file ..\BE\src\my.passphrase --decrypt --output MTR241_20111124.htm MTR241_20111124.htm.gpg 
Reading passphrase from file descriptor 3 
gpg: CAST5 encrypted data 
gpg: encrypted with 1 passphrase 
gpg: WARNING: message was not integrity protected 

동일한 메시지가 java exec 및 명령 프롬프트에서 인쇄됩니다.

C:\Eclipse\workspace2\sync_inbox>gpg.exe --passphrase-file ..\BE\src\my.passphrase --decrypt --output MTR241_20111124.htm MTR241_20111124.htm.gpg 
inp>gpg.exe --passphrase-file ..\BE\src\my.passphrase --decrypt --output MTR241_20111124.htm MTR241_20111124.htm.gpg 
gpg.exe --passphrase-file ..\BE\src\my.passphrase --decrypt --output MTR241_20111124.htm MTR241_20111124.htm.gpg 
gpg: CAST5 encrypted data 
gpg: encrypted with 1 passphrase 
gpg: WARNING: message was not integrity protected 

지금까지 충분한

Case2 : 명령에서 예상대로 출력 파일이 이미 존재할 때 내가 대체 할 것인지 묻는 메시지가하라는 메시지를 표시합니다.

C:\Eclipse\workspace2\sync_inbox>gpg.exe --passphrase-file ..\BE\src\my.passphrase --decrypt --output MTR241_20111124.htm MTR241_20111124.htm.gpg 
Reading passphrase from file descriptor 3 
gpg: CAST5 encrypted data 
gpg: encrypted with 1 passphrase 
File `MTR241_20111124.htm' exists. Overwrite? (y/N) y 
gpg: WARNING: message was not integrity protected 

하지만이 출력은이 첫 번째 줄 뒤에 중단되는 java 프로그램에서 가져온 것입니다. 그것은 콘솔에 어떤 줄도 출력하지 않습니다. 콘솔에 'y'를 입력하면 입력 및 처리가 허용되지 않습니다. 단순히 멈 춥니 다. 나는 수동으로 taskkill/F/IM gpg.exe 프로세스를 죽여야 만한다. 그런 다음 자바 콘솔 프로그램은 더 많은 명령과 프로세스를 받아 들인다. 물론 작품의

C:\Eclipse\workspace2\sync_inbox>gpg.exe --passphrase-file ..\BE\src\my.passphrase --decrypt --output MTR241_20111124.htm MTR241_20111124.htm.gpg 
inp>gpg.exe --passphrase-file ..\BE\src\my.passphrase --decrypt --output MTR241_20111124.htm MTR241_20111124.htm.gpg 
gpg.exe --passphrase-file ..\BE\src\my.passphrase --decrypt --output MTR241_20111124.htm MTR241_20111124.htm.gpg 
    --hangs here-- 

정상적인 대화 형 명령은, 예 말할 : 그래서 여기

F:\eclipse\workspace\HTMLProcessor\BEQuery>copy hello.txt world.txt 
inp>copy hello.txt world.txt 
copy hello.txt world.txt 
Overwrite world.txt? (Yes/No/All): y 
inp>y 
y 
     1 file(s) copied. 

는 그것이할지 여부 프롬프트를 요청하는 경우에만 GPG의 출력 스트림을 캡처에 실패하는 이유는 내 질문입니다 기존 출력 파일을 대체하십시오.

나는 Runtime.exec(), ProcessBuilder, Plexus-Utils, ExpectJ, Ant를 사용하여이 gpg.exe를 자바 프로그램 내에서 실행하려고 시도했다. 모두 동일한 결과가 프로세스의 출력 스트림을 캡처하는 데 실패했다. 특별한 경우. 심지어 bat 파일을 작성하여 gpg --decrypt을 실행하려고 시도했지만 심지어 특수한 경우에 출력 스트림을 캡처하는 데 실패했습니다.

나는 gpg.exe의 기원 인 것이 중요하다고 생각합니다. 글쎄, 휴대용 git 배포판에서 bin 폴더에 gpg.exe를 사용할 수있다.

내 질문은 여전히 ​​오류 자바 코드

package com.ycs.ezlink.scheduler.cmd; 

import java.io.BufferedReader; 
import java.io.BufferedWriter; 
import java.io.IOException; 
import java.io.InputStream; 
import java.io.InputStreamReader; 
import java.io.OutputStream; 
import java.io.OutputStreamWriter; 
import java.io.PrintWriter; 
import org.apache.log4j.Logger; 

public class CmdRunner { 
    private static Logger logger = Logger.getLogger(CmdRunner.class); 

    static class StreamGobbler extends Thread 
    { 
     InputStream is; 
     String type; 

     StreamGobbler(InputStream is, String type) 
     { 
      this.is = is; 
      this.type = type; 
     } 

     public void run() { 
      try { 
       System.out.println("in run!"); 
        System.out.println(type); 
        final byte[] buffer = new byte[1]; 
        for (int length = 0; (length = is.read(buffer)) != -1;) { 
         System.out.write(buffer, 0, length); 
        } 
       } catch (IOException ioe) { 
        ioe.printStackTrace(); 
       } 
     } 
    } 

    public static int process(String cmd){ 
     int exitVal = 0; 
     try { 
      Runtime rt = Runtime.getRuntime(); 
      Process proc = rt.exec(cmd); 
      // any error message? 
      StreamGobbler errorGobbler = new 
       StreamGobbler(proc.getErrorStream(), "ERROR");    

      // any output? 
      StreamGobbler outputGobbler = new 
       StreamGobbler(proc.getInputStream(), "OUTPUT"); 

      // kick them off 
      errorGobbler.start(); 
      outputGobbler.start(); 

      // any error??? 
      System.out.println("Waiting for cmd process to complete "); 
      exitVal = proc.waitFor(); 
      System.out.println("ExitValue: " + exitVal); 
     } catch (IOException e) { 
      e.printStackTrace(); 
     } catch (InterruptedException e) { 
      e.printStackTrace(); 
     }  
     return exitVal; 
    } 

    public static void main(String[] a) throws IOException, InterruptedException, TimeoutException, ExpectJException { 
     String gzipCmd = "gpg.exe --passphrase-file C:/Eclipse/workspace2/BE/src/my.passphrase --decrypt --output C:/Eclipse/workspace2/sync_inbox/MTR241_20111124.htm C:/Eclipse/workspace2/sync_inbox/MTR241_20111124.htm.gpg"; 
     //CmdRunner.process(gzipCmd); ///--fails 
     //ProcessBuilder pb = new ProcessBuilder("gpg", "--passphrase-file", "C:/Eclipse/workspace2/BE/src/my.passphrase", 
     "--decrypt","--output","C:/Eclipse/workspace2/sync_inbox/MTR241_20111124.htm", 
     "C:/Eclipse/workspace2/sync_inbox/MTR241_20111124.htm.gpg"); ///--fails 
     ProcessBuilder pb = new ProcessBuilder ("cmd"); 
     pb.redirectErrorStream(true); 
     Process process = pb.start(); 
     OutputStream stdin = process.getOutputStream(); 
     InputStream stderr = process.getErrorStream(); 
     InputStream stdout = process.getInputStream(); 
     StreamGobbler errorGobbler = new StreamGobbler(stderr, "ERROR");    
     errorGobbler.start(); 
     StreamGobbler stdoutGobbler = new StreamGobbler(stdout, "DEBUG");    
     stdoutGobbler.start(); 

     BufferedReader scan = new BufferedReader(new InputStreamReader(System.in)); 
     String line; 
     while ((line = scan.readLine())!= null) { 
       String input = line; 
       System.out.println("inp>"+input); 
       if (input.trim().equals("exit")) { 
        stdin.write("exit\r\n".getBytes()); 
        stdin.flush(); 
        break; 
       } else { 
        stdin.write((input+"\r\n").getBytes()); 
        stdin.flush(); 
       } 
      } 
     System.out.println("exited.."); 
     int returnCode = process.waitFor(); 
     System.out.println(returnCode); 
    } 
} 
을 지적하고 싶으신 분들에게 정말 길고 지루한되었다

마지막 단어 나는 gpg --batch 옵션을 사용하는 경우, y/N 입력하기에 더 이상 프롬프트 그래서 부드럽게 돌아갑니다. 그러나 나는 단지 궁금해서, 왜이 문제가 있을지 알고 있습니다. gpg.exe가 원래 플랫폼과 같은 유닉스/리눅스 용으로 작성되었다는 느낌이 들기는하지만 입출력 파일 리다이렉션이있을 수 있지만 그 근본 원인에 대해 더 알고 싶습니다. 그래서 다음에 무엇을 알 수 있습니까? 찾을 것이다.

답변

2

터미널에서 보는 출력은 표준 출력 스트림, 표준 오류 스트림 및 콘솔의 병합 결과입니다. 표준 출력과 표준 오류 스트림을 캡처 할 수 있습니다. 하지만 콘솔을 캡처 할 수는 없습니다. 이것이 gpg 의도적으로이 직접 콘솔을 사용하여 캡처하지 못하게하는 이유입니다. 왜 그들이 이것을하는지는 논쟁의 여지가 있습니다.

결론 : 콘솔을 직접 처리하는 프로그램의 입력 또는 출력 스트림을 캡처 할 수 없습니다.

+0

그러나 자바 프로세스가 gpg 출력을 볼 수 있다는 것을 알았습니다. gpg에 대한 입력 [y/N] 입력을 보낼 수 없습니다. Btw 방금이 콘솔에 대해 알게되었습니다. [http://www.robvanderwoude.com/battech_redirection.php](http://www.robvanderwoude.com/battech_redirection.php). 도와 주셔서 감사합니다 –

관련 문제