package com.blubi.branchmaster.commandline;

import java.io.BufferedReader;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.IOException;
import java.io.InputStreamReader;

import org.apache.commons.exec.CommandLine;
import org.apache.commons.exec.DefaultExecutor;
import org.apache.commons.exec.PumpStreamHandler;

import com.blubi.branchmaster.Main;

public abstract class AbstractCommandLineRunner {

	private static long stat_total_ms = 0;
	private static long stat_total_calls = 0;
	
	File homedir = null;
		
	public AbstractCommandLineRunner(File homedir) {
		this.homedir = homedir;
	}

	public static int run2(String command) {
		try {
			ByteArrayOutputStream stdout = new ByteArrayOutputStream();
		    PumpStreamHandler psh = new PumpStreamHandler(stdout);
		    CommandLine cl = CommandLine.parse(command);
		    DefaultExecutor exec = new DefaultExecutor();
		    exec.setStreamHandler(psh);
		    int exitValue = exec.execute(cl);
		    System.out.println(stdout.toString());
		    return exitValue;	    	
		} catch (Exception e)  {
			System.out.println(e.getMessage());
			//return handleException(e);
			return -1;
		}
	}

	public static void main(String[] args) {
		run2("git --hel");
	}
	
	protected int run(String command) {
		try {
			long startTime = System.currentTimeMillis();			
	        Process p = Runtime.getRuntime().exec(command,null, this.homedir);
	        int exitCode = p.waitFor();
	        long runTime = System.currentTimeMillis()-startTime;
	        stat_total_ms += runTime;
	        stat_total_calls++;
	        Main.debuglog("RUN("+runTime+"ms): "+command+ " in ["+ this.homedir.getAbsolutePath() +"]");
	        BufferedReader input = new BufferedReader(new InputStreamReader(p.getInputStream()));
	        String line; 
	        while ((line = input.readLine()) != null) {
	        	handle(line);
	        }
	        
	        BufferedReader error = new BufferedReader(new InputStreamReader(p.getErrorStream()));
	        while ((line = error.readLine()) != null) {
	        	handleErr(line);	    
	        }
	        
	        return exitCode;

		} catch (IOException e)  {
			return handleException(e);
		} catch (InterruptedException e) {
			return handleException(e);
		}		
	}
	
	protected void handle(String line) {
        System.out.println(line);
	}
	
	protected void handleErr(String line) {
        System.out.println("ERROR: "+ line);		
	}
	
	protected int handleException(Throwable e) {
		throw new RuntimeException(e);		
	}
	
	
	public static void output_stat() {
		System.out.println("\n-- Stats --");
		System.out.println("Total time in commands: "+stat_total_ms+"ms");
		System.out.println("Total commands: "+stat_total_calls);
		
	}
}
@@ -73,46 +73,8 @@
 er;%0A
-import java.io.ByteArrayOutputStream;%0A
 impo
@@ -245,16 +245,64 @@
 ecutor;%0A
+import org.apache.commons.exec.LogOutputStream;%0A
 import o
@@ -634,23 +634,15 @@
 lic 
-static 
 int run
-2
 (Str
@@ -671,67 +671,447 @@
 %0A%09%09%09
-ByteArrayOutputStream stdout = new ByteArrayOutputStream();
+LogOutputStream outStrm = new LogOutputStream() %7B%0A%09%09%09    @Override protected void processLine(String line, int level) %7B%0A%09%09%09    %09System.out.println(%22out: %22+line+%22; %22+level);%0A%09%09        handle(line);%0A%09%09      %7D%09%09%09%0A%09%09%09%7D;%0A%09%09%09%0A%09%09%09LogOutputStream errStrm = new LogOutputStream() %7B%0A%09%09%09    @Override protected void processLine(String line, int level) %7B%0A%09%09%09    %09System.out.println(%22err: %22+line+%22; %22+level);%0A%09%09        handleErr(line);%0A%09%09      %7D%0A%09%09%09%7D;%0A
 %0A%09%09 
@@ -1159,22 +1159,31 @@
 Handler(
-std
 out
+Strm,errStrm
 );%0A%09%09   
@@ -1280,16 +1280,105 @@
 utor();%0A
+%09%09    exec.setWorkingDirectory(this.homedir);%0A%09%09    exec.setExitValues(new int%5B%5D %7B0,1%7D);%0A
 %09%09    ex
@@ -1403,16 +1403,23 @@
 r(psh);%0A
+%09%09    %0A
 %09%09    in
@@ -1454,53 +1454,8 @@
 l);%0A
-%09%09    System.out.println(stdout.toString());%0A
 %09%09  
@@ -1514,49 +1514,8 @@
 %0A%09%09%09
-System.out.println(e.getMessage());%0A%09%09%09//
 retu
@@ -1540,1111 +1540,15 @@
 (e);
-%0A
 %09%09%09
-return -1;%0A%09%09%7D%0A%09%7D%0A%0A%09public static void main(String%5B%5D args) %7B%0A%09%09run2(%22git --hel%22);%0A%09%7D%0A%09%0A%09protected int run(String command) %7B%0A%09%09try %7B%0A%09%09%09long startTime = System.currentTimeMillis();%09%09%09%0A%09        Process p = Runtime.getRuntime().exec(command,null, this.homedir);%0A%09        int exitCode = p.waitFor();%0A%09        long runTime = System.currentTimeMillis()-startTime;%0A%09        stat_total_ms += runTime;%0A%09        stat_total_calls++;%0A%09        Main.debuglog(%22RUN(%22+runTime+%22ms): %22+command+ %22 in %5B%22+ this.homedir.getAbsolutePath() +%22%5D%22);%0A%09        BufferedReader input = new BufferedReader(new InputStreamReader(p.getInputStream()));%0A%09        String line; %0A%09        while ((line = input.readLine()) != null) %7B%0A%09        %09handle(line);%0A%09        %7D%0A%09        %0A%09        BufferedReader error = new BufferedReader(new InputStreamReader(p.getErrorStream()));%0A%09        while ((line = error.readLine()) != null) %7B%0A%09        %09handleErr(line);%09    %0A%09        %7D%0A%09        %0A%09        return exitCode;%0A%0A%09%09%7D catch (IOException e)  %7B%0A%09%09%09return handleException(e);%0A%09%09%7D catch (InterruptedException e) %7B%0A%09%09%09return handleException(e);%0A%09%09%7D%09%09
+%0A%09%09%7D
 %0A%09%7D%0A
@@ -1805,18 +1805,16 @@
 %09%09%0A%09%7D%0A%09%0A
-%09%0A
 %09public 

Use apache.commons.exec instead of runtime.exec. Hopefully fixes mysterious hangs on some systems.