Search code examples
javascriptjava-8nashorn

Java 8 Nashorn whitespace issue


UPDATE:

I have a gross solution that works, but I don't like it:

jjs> NANO_HOME = '"/Users/XXXXXX/Desktop/TEST DIR"'; jjs> $EXEC('xargs ls',"${NANO_HOME}");


I am using Java 8 Nashorn to do some shell scripting, and I'm having issues with listing files in a directory if the directory name contains a space:

$ jjs -scripting
jjs> `ls /Users/XXXXXX/Desktop/`
TEST DIR
jjs> `ls /Users/XXXXXX/Desktop/TEST DIR`

jjs> $ERR
ls: /Users/XXXXXX/Desktop/TEST: No such file or directory
ls: DIR: No such file or directory  

jjs> `ls "/Users/XXXXXX/Desktop/TEST DIR"`

jjs> $ERR
ls: "/Users/XXXXXX/Desktop/TEST: No such file or directory
ls: DIR": No such file or directory

jjs> `ls /Users/XXXXXX/Desktop/TEST\u0020DIR`

jjs> $ERR
ls: /Users/XXXXXX/Desktop/TEST: No such file or directory
ls: DIR: No such file or directory

jjs> `ls /Users/XXXXXX/Desktop/TEST\ DIR`

jjs> $ERR
ls: /Users/XXXXXX/Desktop/TEST: No such file or directory
ls: DIR: No such file or directory

I've tried dozens of variations and nothing works...


Solution

  • Unfortunately it looks like the backquote syntax for invoking system commands (as well as the $EXEC function, which does the same thing) mishandles arguments that contain whitespace.

    The source code is in the exec function in ScriptingFunctions.java file. Unfortunately it uses a plain StringTokenizer to split the string into an array of argument strings, which are then passed to ProcessBuilder. This means that whitespace, quoting, backslashes, and so forth, are not taken into account.

    I'd say this is a bug. There should be a way to pass an argument array directly to $EXEC instead of having it parse the string into arguments, but I'm not aware of one.

    UPDATE

    Enhancement request JDK-8049300 filed.