Search code examples
javascriptjavajava-8nashorn

How to invoke Nashorns `ScriptFunction` callback from Java?


I have some javascript code that is executed onto my object in Java Nashorn:

scriptEngine.eval("my.fn(function(a,b) {...}");

I can create method fn in my class that receives the ScriptFunction, but I don't get how to pass arguments and invoke this function from Java.

EDIT

I can make fn(Runnable) or fn(Callable) but I still don't know how to pass arguments to any of these two, from my Java implementation of fn?


Solution

  • Please avoid using any nashorn internal types like jdk.nashorn.internal.runtime.ScriptFunction in your Java code. With jdk9, jigsaw modular access checks prevent accessing such types from user code!

    If you do want a callback to be passed to your Java code which is implemented in Nashorn script, there are two approaches:

    1) Accept any @FunctionalInterface type in your code (https://docs.oracle.com/javase/8/docs/api/java/util/function/package-summary.html) like Supplier, Consumer, Function etc. Nashorn allows any script function to be passed as argument when a functional interface object is needed in java code. From script, you can pass a script function. On java side, you just invoke just as an interface method (like "get", "accept", "apply" etc. - these are functional methods on Supplier, Consumer, Function respectively)

    2) Accept jdk.nashorn.api.scripting.JSObject ( https://docs.oracle.com/javase/8/docs/jdk/api/nashorn/jdk/nashorn/api/scripting/JSObject.html) type argument in your Java code. From script, you can pass a script function as an argument when JSObject is needed in Java call. From Java code, you can invoke "call" method on JSObject [ https://docs.oracle.com/javase/8/docs/jdk/api/nashorn/jdk/nashorn/api/scripting/JSObject.html#call-java.lang.Object-java.lang.Object...- ]