2

I'm trying to run a system command to extract a tar.bz2 file to a specified directory. This is the code:

ProcessBuilder myProc = new ProcessBuilder("tar", "-xjf", "/path/to/MyTarFile.tar.bz2"); 
myProc.directory(new File("/directory/i/want/results/in/"));
myProc.start();
System.out.println(myProc.command());

It runs without error, however the file is deleted and not extracted anywhere.

Any help would be greatly appreciated.

1
  • 3
    Assuming Paul didn't just solve your problem outright, might be worth funneling Process.getInputStream() and Process.getErrorStream() to someplace you can read them. (Or, call ProcessBuilder.redirectErrorStream(true) and just keep an eye on getInputStream().) It could be silently reporting issues that wouldn't cause the Java program to crash. Commented Aug 20, 2010 at 19:08

4 Answers 4

6

I know Runtime.exec() has a really nasty feature where if you don't manually drain STDOUT/STDERR, it effectively appears to hang. I would hope that ProcessBuilder corrected that deficiency, but this page includes this tidbit:

A word of caution about the examples in this tip. It is possible that the examples will deadlock if the subprocess generates enough output to overflow the system. A more robust solution requires draining the process stdout and stderr in separate threads.

So, make sure you're handling Process.getInputStream() and Process.getErrorStream(), as I recommended in the comments; it could solve the problem outright!

Sign up to request clarification or add additional context in comments.

4 Comments

Wow, I would've never caught this. Thanks!
Glad to help, mate. Got bit by this myself; completely baffling, and not fun.
Alternatively, call myProc.redirectErrorStream(true), which redirects standard error into standard output and gets rid of the need for a separate thread.
... and, thanks for the warning that Runtime.exec's replacement will still force me to point those two streams at the bit bucket instead of doing it for me.
3

Change the myProc.start(); line to

  Process p = myProc.start();
  p.waitFor();

That will make sure your program doesn't exit until the tar is finished.

1 Comment

Good suggestion, however I did that and am receiving the same results.
2

Run this to see errors. Perhaps one of your paths is incorrect.

import java.io.File;
import java.io.InputStream;

public class Untar {

public static void main(String[] args) throws Exception {
    ProcessBuilder myProc = new ProcessBuilder("tar", "-xjf", "foo.tar.bz2");
    myProc.directory(new File("newdir"));
    Process p = myProc.start();
    InputStream is = p.getErrorStream();
    int c;
    while( (c = is.read()) != -1 ){
       System.out.print((char)c);
    }
    p.waitFor();
    System.out.println(myProc.command());
}

}

1 Comment

This will also help if stderr buffer is full. But it won't help if the stdout buffer is full.
0

Just tried this code. It works.

Check your paths.

1 Comment

If @BlairHippo's suggestion is correct, it might work for you and not the OP if the OP has a lot more files in his tar file than you do.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.