My application uses a ScriptEngine
to offer plugin-ability to my end-users.
ScriptEngineManager engineManager = new ScriptEngineManager();
ScriptEngine engine = engineManager.getEngineByName("nashorn");
Whenever a user makes changes to his script, then the application replaces the engine instane by a new instance.
String newScript = ...;
engine = engineManager.getEngineByName("nashorn");
engine.eval(newScript);
Two closely related questions:
Should I try to reuse engines and perform some kind of clear()
on them ?
If I just replace my engine with a new instance, should I dispose the previous instance in some way, to avoid memory leaks ? (e.g. I can imagine that the user could manage to create a script that starts a thread.)
The problem is, I cannot find any method that looks like a clear()
or a dispose()
. Does that mean that my current approach is correct ?
You can use a single engine instance but use separate Bindings
objects. Bindings
acts as a top-level program environment, so if you want to evaluate a script into what is basically a "new global scope" then you could do that. Look into javax.script
API docs on how to do this. You can either use ScriptEngine.eval
that takes a Bindings
as second argument or the one that takes ScriptContext
as second argument.
Even if there's no script code surviving from the previous evaluation, you'll save some initialization time as the script engine will already have predefined various JavaScript data-holder classes and property maps ("hidden classes").
Also: yes, everything is garbage collected. There's no need for an explicit "disposal" API.