I’m trying to use kotlin as a scripting language for a jvm application through jsr223 and it works fine however there is some boilerplate to access bindings as they cannot be accessed directly but one ha to grab them from bindings, so as example, I do evaluate a kotlin script as follow:
final CamelContext context = getContext();
final ScriptEngineManager manager = new ScriptEngineManager();
final ScriptEngine engine = manager.getEngineByExtension("kts");
final Bindings bindings = new SimpleBindings();
// Exposed to the underlying script, but maybe better to have
// a nice dsl
bindings.put("builder", this);
bindings.put("context", context);
bindings.put("components", new Components(context));
try (InputStream is = ResourceHelper.resolveMandatoryResourceAsInputStream(context, resource)) {
engine.eval(new InputStreamReader(is), bindings);
}
Then the script looks like:
val builder = bindings["builder"] as org.apache.camel.builder.RouteBuilder
fun from(uri: String): org.apache.camel.model.RouteDefinition = builder.from(uri)
from("timer:tick")
.process().message {
m -> m.headers["MyHeader"] = "MyHeaderValue"
}
.to("log:info")
Is there any way to have bindings bounded to a global scope such as what’s possible when using Java’s nashorn interpreter or Groovy’s DelegatingScript ?
One or the issues with JSR223 is that any form of such binding is non-standard. There is very little “advanced” support to be able to tighten integration even if it is not dependent on the actual language.
What actually “should” work (at least as far as JSR223 is concerned - I haven’t tried this in reality) is using the invoke operator. The problem is that the bindings are geared towards the javascript usecase only. It should be certainly possible for Kotlin to work on any value (exposed through a binding) that implements the invoke operator. It might also be possible for the Kotlin scripting system to automatically handle Kotlin (and Java) lambda’s as they have clear semantics. The main thing is you cannot expose functions, only objects. But you can create objects that forward to functions .