By default, the run task for my SBT build executes my main class found (automatically) in src/main/scala/
.
How can I add a new task for a project that behaves just like the run task but finds a main class in src/util/scala
? The task should run the util main method with src/main/scala
on the classpath.
I am using SBT 0.12.4 with a full multi project configuration.
The following defines a new configuration that compiles sources from src/util/scala
and defines util:run
and util:run-main
to run main classes from the new configuration. The compiled sources from src/main/scala
are available on the classpath when compiling and running.
import sbt._
import Keys._
object MyBuild extends Build
{
// Define a new configuration named `util`.
// Extending `Compile` means the main classpath is available to `util`
lazy val Util = config("util").extend(Compile)
// Add the new configuration to the project.
// Add the new settings.
lazy val root = Project("root", file(".")).configs(Util).settings( utilSettings : _*)
// Add the basic source, compilation, and packaging settings
// as well as custom run methods.
lazy val utilSettings = inConfig(Util)( Defaults.configSettings ++ utilRunSettings )
// Settings that define `run` and `run-main` to use the
// classpath from the enclosing configuration.
// (The standard `run` methods use the `Runtime` configuration.
lazy val utilRunSettings = Seq(
run <<= Defaults.runTask(fullClasspath, mainClass in run, runner in run),
runMain <<= Defaults.runMainTask(fullClasspath, runner in run)
)
}
(Was tested on 0.13, but should work on 0.12.)
I don't think sbt will find code that you put in src/util/... it should go in src/main/scala, src/test/scala, etc. You might want to add utility classes to some kind of "util" package, maybe in src/main/com/example/util, or put them in a sub project or dependent project, but sbt isn't really designed (afaik) to be able to handle arbitrary directory structures.
As far as setting up multiple main methods, sbt run, if it finds multiple main methods in src/main/scala, will let you choose which one to call.
If it's in an external jar you may need to: Configuring sbt project to include external Main methods in "sbt run"
What I usually do is run sbt console
and then just import and call the main method directly from there. For example:
sbt console
import com.example.Main
Main(new String[])
Since you have sub-projects, if one of your projects is "util," you should be able to use something like sbt util/run
to run a main method in util/src/main/scala.
You should also be able to use sbt "util/run-main com.example.MainClass"
if you have multiple main methods in one project.
You might also consider the sbt start-script plugin: https://github.com/sbt/sbt-start-script
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With