scala-cli
scala-cli copied to clipboard
Allow for ammonite-style import $file in scripts with using directives
Right now scala-cli requires passing in all scala source dependencies as arguments, including transitive dependencies. It would be nice to have ammonite-style import $file syntax, maybe with the existing using directives. Maybe something like this:
//> using import mod1 // search for mod1.sc or mod1.scala in the search path
//> using import "./mod1.sc" // search for mod1.sc in same directory as this script
It would be great to have a search path environment variable for scripts similar to CLASSPATH, along with a global property to tell the interpreter where to search for scripts.
Hello @benwbooth
It would be nice to have ammonite-style import $file
We are thinking of something similar in https://github.com/VirtusLab/scala-cli/issues/934 however we want to use a more straightforward approach - we simply want to use just paths (no magic about extensions) and make key more obvious for newcomers that do not know ammonite.
It would be great to have a search path environment variable for scripts similar to CLASSPATH, along with a global property to tell the interpreter where to search for scripts.
I am not a big fun of configuration by env variables but I am not saying no :) Could you provide some use cases that you see for such search path?
I am not a big fun of configuration by env variables but I am not saying no :) Could you provide some use cases that you see for such search path?
A script lookup path is a common feature in programming languages. Perl has PERL5LIB, python has PYTHONPATH, C/C++ has CPATH etc. The path is also configurable using the -l argument or the use lib statement in perl. Having a script lookup path allows the user to avoid having to hard-code paths to script files or use relative paths that could break if the parent script is moved into another directory. There should be three ways to set the module lookup path:
- using a directive in the source file e.g.
use libin perl - passing an argument to
scala-clisuch as-lin perl - or using an environment variable such as
SCALAPATH. An environment variable probably should not be the first choice for setting up the script search path, but it can be useful in cases where you need to set the search path of a set of scripts you cannot modify such as container images. Setting an environment variable will also allow the change in search path to take effect for any subprocesses as well as the current process since the environment variables will be inherited.
Would like to show support for this feature. I've seen that scripts are already supporting something along these lines, but I'd like the same support for regular Scala files. I like what @romanowski is suggesting above.
One thing that's not mentioned here regarding motivation: we should make importing scala files as easy as it is in languages such as TypeScript, where it's kind of a language built-in. Just treating files as dependencies makes for a very intuitive way of specifying dependencies across modules.
Given foo.scala, mod1/bar.scala, ideally we would use this expression to import everything defined in bar.scala:
import mod1.bar.*
Note it's important to specify both folder and file name so that scala-cli doesn't have to build a reverse index of Scala sources defined in mod1/ and the symbols it contains. This way, scala-cli can compile only the file being imported.
Up to now, what we had in mind is supporting something along those lines:
//> using sources "core/", "extras/"
(This would add the core and extras directories accessible from the directory of the source file where this statement is put.)
That's kind of simpler to implement in the short term: we would only have to process using directives of all initial input sources (no compilation needed), add any new sources, and recurse on that until no new sources get added.
Having imports like import mod1.bar.* automatically pull mod1/bar.scala in the inputs goes significantly beyond that, and would need to be discussed with the compiler team IMO (that would likely involve compiler internals, so this would be only for newer Scala versions, plus this somehow adds new meaning to imports, so is kind of a language evolution). I'm not against the idea though.
Tha main part of this request has been satisfied with the addition of the using file directive from #934 (PR #1157).
The rest regarding the script's search path is a duplicate of #1322 so I'll close this.