I use SBT plugin for IntelliJ and I have created a scala project with the following build settings: Build.scala:
lazy val root =
Project("root", file("."))
.configs( IntegrationTest )
.settings( Defaults.itSettings : _*)
build.sbt:
<setting some parameters>
libraryDependencies += "org.scalatest" % "scala-test_2.10" % "1.0.8" % "test,it"
Now I end up with src/main
, src/test
and src/it
in my project structure. I now can run compile
, test
and it:test
from both SBT console in IntelliJ and in SBT repl. So all is great at this point.
The only problem I yet to figure out is how to debug integration tests. I have added a scalatest configuration that runs test:compile
before launch and this gets me going with unit test debug. I try to create a new Debug configuration for integration tests, but can't figure out how to point it to src/it
to find the tests. I tried to debug a specific test by changing "Test kind" to class and pointing to a specific test class, but keep getting the following exception:
Unable to load a Suite class. This could be due to an error in your runpath. Missing class: it.AddPersonSpec
java.lang.ClassNotFoundException: it.AddPersonSpec
at java.net.URLClassLoader$1.run(URLClassLoader.java:366)
at java.net.URLClassLoader$1.run(URLClassLoader.java:355)
at java.security.AccessController.doPrivileged(Native Method)
at java.net.URLClassLoader.findClass(URLClassLoader.java:354)
at java.lang.ClassLoader.loadClass(ClassLoader.java:425)
at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:308)
at java.lang.ClassLoader.loadClass(ClassLoader.java:358)
at org.scalatest.tools.Runner$$anonfun$22.apply(Runner.scala:1962)
at org.scalatest.tools.Runner$$anonfun$22.apply(Runner.scala:1960)
at scala.collection.TraversableLike$$anonfun$filter$1.apply(TraversableLike.scala:264)
at scala.collection.immutable.List.foreach(List.scala:318)
at scala.collection.TraversableLike$class.filter(TraversableLike.scala:263)
at scala.collection.AbstractTraversable.filter(Traversable.scala:105)
at org.scalatest.tools.Runner$.doRunRunRunDaDoRunRun(Runner.scala:1960)
at org.scalatest.tools.Runner$$anonfun$runOptionallyWithPassFailReporter$2.apply(Runner.scala:850)
at org.scalatest.tools.Runner$$anonfun$runOptionallyWithPassFailReporter$2.apply(Runner.scala:849)
at org.scalatest.tools.Runner$.withClassLoaderAndDispatchReporter(Runner.scala:2221)
at org.scalatest.tools.Runner$.runOptionallyWithPassFailReporter(Runner.scala:848)
at org.scalatest.tools.Runner$.run(Runner.scala:706)
at org.scalatest.tools.Runner.run(Runner.scala)
at org.jetbrains.plugins.scala.testingSupport.scalaTest.ScalaTestRunner.runScalaTest2(ScalaTestRunner.java:144)
at org.jetbrains.plugins.scala.testingSupport.scalaTest.ScalaTestRunner.main(ScalaTestRunner.java:35)
When I look into "Project Structure" -> "Modules", I see that src/it/scala
is under "Test source folders" category. Not sure where else to look now ...
Update: I had an sbt configuration problem. I used project name "root" in Build.scala and other name in build.sbt. This created two module configurations for IntelliJ. I fixed that and now I can't reconcile IntelliJ and sbt settings for my only module.
The effect that I see now is that after I run gen-idea from sbt console and reload the project, my integration test looks fine for a little while (while sbt is being updated). I can even get to a definition of 'And' method defined in Scalatest. After a few seconds, however, it 'looses' a reference to scalatest lib (when sbt is done updating). When I go to "Project Structure" -> "Modules", I don't see src/it/scala
anywhere. If I add it manually to test source IntelliJ can resolve scalatest again. After I run gen-idea
it disappears. Rinse and repeat.
Note that remote debugger solution proposed by Eugene does not work for me. I run sbt as a server and attach IntelliJ, but when I run it:test
it does not stop on breakpoint. I think it is because integration test source is not considered to be a part of source/test by IntelliJ.
If I first add src/it/scala
in project settings and then try to use remote debugger before running gen-idea
, then SBT crashes with OutOfMemory. So I'm completely stumped at this point...
Any thoughts are highly appreciated.
In IntelliJ, right-click on the project, go to Open Module Settings
, select the Paths
tab, and change Test output path
from .../target/scala-2.11/test-classes
to .../target/scala-2.11/it-classes
. That way, you can debug integration tests just like normal tests.
You have to change it back before debugging a normal test. Also, importing the sbt project into IntelliJ again wipes the setting.
That's how I debug SBT projects:
Add to ~/.sbtconfig
SBT_OPTS="-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=5005"
Attach Intellij Idea to running sbt process with Remote Debug configuration: http://www.jetbrains.com/idea/webhelp/run-debug-configuration-remote.html
Profit! Add breakpoints in you project code.
Note that in this configuration Idea will be attached to SBT JVM, not only to you project files, so you can debug your build file too.
If you use "fork in Test := true" option I guess it's possible to pass this config with jvm args config option, but as I can see from you project definition, you don't fork your tests.
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