From inside jShell script, is it possible to access or register variables that are defined in code that's also creating JShell?
Currently there seems to be no mechanism to either access or register a variable to Shell instance, or return none string types from inside JShell (like objects or lambda etc.)
ex:
import jdk.jshell.JShell; import jdk.jshell.JShellException; import jdk.jshell.SnippetEvent; import java.util.List; public class Main { public static void main(String[] args) throws JShellException { var localVar = 1; JShell shell = JShell.create(); // How to register localVar variable with shell instance or access variables from scope List events = shell.eval("var x = localVar;"); SnippetEvent event = events.get(0); System.out.println("Kind: " + event.snippet().kind() + ", Value: " + event.value()); } }
While you can't access local names like in your example, you can create a JShell instance that executes in the same JVM that created it. For this you would use the
LocalExecutionControl
. Using this execution control you could movelocalVar
to a static field in yourMain
class and then access it from "inside" the JShell code withMain.localVar
.Unfortunately as the API is designed to support execution providers that could be in a different process or even a different machine, the return type is a string. If you are interested in a hack, the IJava jupyter kernel needed to an implementation of
eval
that returned anObject
which ended up using anExecutionControl
implementation based on theDirectExecutionControl
that stored the result of aneval
call in a map and returned a unique id to reference that result. Then using the shell you would have to lookup the result from the id returned byeval
(think of something likeresults.get(eval(sourceCode))
). That implementation is on github in IJavaExecutionControl.java and IJavaExecutionControlProvider.java with a sample usage in CodeEvaluator.java#L72 if you are interested in taking any of it (MIT license).