I\'m trying to evaluate javascript in Java by using the ScriptEngine class. Here is a short example of what I am trying to do:
import javax.script.ScriptEngineMa
Note: The following is for Java 8, using the Nashorn engine.
First, to make the code compile, remove the .value
from the println()
statement. obj
is declared to be type Object
, and Object
doesn't have a value
field.
Once you do that, you get the following exception when running the code:
Exception in thread "main" javax.script.ScriptException: <eval>:1:25 Invalid return statement
var obj = { value: 1 }; return obj;
^ in <eval> at line number 1 at column number 25
That is because you don't have a function, so you cannot call return
. The return value of the script is the value of the last expression, so just say obj
.
Now it will run and print [object Object]
. To see what type of object you got back, change to println(obj.getClass().getName())
. That will print jdk.nashorn.api.scripting.ScriptObjectMirror. I've linked to the javadoc for your convenience.
ScriptObjectMirror
implements Bindings which in turn implements Map<String, Object>
, so you can call get("value")
.
Working code is:
import javax.script.*;
public class Test {
public static void main(String[] args) throws ScriptException {
ScriptEngine engine = new ScriptEngineManager().getEngineByName("js");
Bindings obj = (Bindings)engine.eval("var obj = { value: 1 }; obj; ");
Integer value = (Integer)obj.get("value");
System.out.println(value); // prints: 1
}
}
UPDATE
The whole point was to create an object with functions, is that possible with this engine? There isn't a Function object.
Example for how to do that:
import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;
import jdk.nashorn.api.scripting.ScriptObjectMirror;
public class Test {
public static void main(String[] args) throws Exception {
String script = "var f = {\n" +
" value: 0,\n" +
" add: function(n) {\n" +
" this.value += n;\n" +
" return this.value;\n" +
" }\n" +
"};\n" +
"f; // return object to Java\n";
ScriptEngine engine = new ScriptEngineManager().getEngineByName("js");
ScriptObjectMirror obj = (ScriptObjectMirror)engine.eval(script);
System.out.println("obj.value = " + obj.getMember("value"));
System.out.println("obj.add(5): " + obj.callMember("add", 5));
System.out.println("obj.add(-3): " + obj.callMember("add", -3));
System.out.println("obj.value = " + obj.getMember("value"));
}
}
OUTPUT
obj.value = 0
obj.add(5): 5.0
obj.add(-3): 2.0
obj.value = 2.0