Either there is a bug in Apache Commons Exec, or I am using the API wrong, but when I use the CommandLine
class to add a argument that contains spaces, some quotes are added and are then part of the argument that is given.
For example: When I call java "what version"
I get java.lang.NoClassDefFoundError: what version
, and when I call java "\"what version\""
(which contains escaped quotes, that are part of the command line argument itself), I get java.lang.NoClassDefFoundError: "what version"
.
So the following test fails, because as you can see in the last line, Apache Exec is producing the latter version where it should have produced the first version:
@Test
public void testArgumentQuoting() throws Exception {
DefaultExecutor executor = new DefaultExecutor();
DefaultExecuteResultHandler resultHandler = new DefaultExecuteResultHandler();
ByteArrayOutputStream out = new ByteArrayOutputStream();
PumpStreamHandler streamHandler = new PumpStreamHandler(out, out);
executor.setStreamHandler(streamHandler);
CommandLine cmdLine = new CommandLine("java");
cmdLine.addArgument("what version");
executor.execute(cmdLine, resultHandler);
resultHandler.waitFor();
String resultPattern = "Exception in thread \"main\" java\\.lang\\.NoClassDefFoundError: ([\\w \"]+)";
Pattern pattern = Pattern.compile(resultPattern);
Matcher matcher = pattern.matcher(out.toString());
Assert.assertTrue(matcher.find());
// Note: Result should be <what version> and NOT <"what version">!
Assert.assertEquals("what version", matcher.group(1));
}
Now I want to know:
- Is this a bug?
- If so: Is there a way to circumvent this problem (a workaround)?
- If not: What am I doing wrong?
Edit: I am trying to execute a process which I think fewest people will have on their machine. So I am using java
instead as this command should be available on all machines where people develop Java. My point is that the wrong runtime argument is passed to the external process, containing escaped quotes, which it shouldn't.
Edit: I made this a filed bug for commons exec at Jira.
What class are you trying to execute? You're not specifying exactly what you want Java to execute. That needs to be your second argument.
In other words, if you're trying to run com.mycompany.MyExecutable, your code should look like this:
You can either append arguments after the CommandLine object is created.
Apache common exec has
addArgument
method withhandleQuoting
flag. If it's turned on, then it wraps arguments in quotation marks.By default it's turned on
How about trying it this way as in the tutorial, to see if that makes a difference?
This seems to be a real bug in Apache Commons Exec, which to date has not been fixed.
you can try the next example it works for me :