Use application-test.conf for typed testkit, #25708
* solves the problem that previously it loaded application.conf if no Config parameter is used, but not otherwise * application.conf should normally not be used by tests, but if someone prefer that it's easy enough to use it via `ConfigFactory.load()` or via include in application-test.conf
This commit is contained in:
parent
4561994a59
commit
af77bf3fb0
11 changed files with 213 additions and 9 deletions
|
|
@ -27,6 +27,10 @@ object ActorTestKit {
|
||||||
* e.g. threads will include the name.
|
* e.g. threads will include the name.
|
||||||
* When the test has completed you should terminate the `ActorSystem` and
|
* When the test has completed you should terminate the `ActorSystem` and
|
||||||
* the testkit with [[ActorTestKit#shutdownTestKit]].
|
* the testkit with [[ActorTestKit#shutdownTestKit]].
|
||||||
|
*
|
||||||
|
* Config loaded from `application-test.conf` if that exists, otherwise
|
||||||
|
* using default configuration from the reference.conf resources that ship with the Akka libraries.
|
||||||
|
* The application.conf of your project is not used in this case.
|
||||||
*/
|
*/
|
||||||
def create(): ActorTestKit =
|
def create(): ActorTestKit =
|
||||||
new ActorTestKit(scaladsl.ActorTestKit(TestKitUtils.testNameFromCallStack(classOf[ActorTestKit])))
|
new ActorTestKit(scaladsl.ActorTestKit(TestKitUtils.testNameFromCallStack(classOf[ActorTestKit])))
|
||||||
|
|
@ -38,10 +42,26 @@ object ActorTestKit {
|
||||||
* e.g. threads will include the name.
|
* e.g. threads will include the name.
|
||||||
* When the test has completed you should terminate the `ActorSystem` and
|
* When the test has completed you should terminate the `ActorSystem` and
|
||||||
* the testkit with [[ActorTestKit#shutdownTestKit]].
|
* the testkit with [[ActorTestKit#shutdownTestKit]].
|
||||||
|
*
|
||||||
|
* Config loaded from `application-test.conf` if that exists, otherwise
|
||||||
|
* using default configuration from the reference.conf resources that ship with the Akka libraries.
|
||||||
|
* The application.conf of your project is not used in this case.
|
||||||
*/
|
*/
|
||||||
def create(name: String): ActorTestKit =
|
def create(name: String): ActorTestKit =
|
||||||
new ActorTestKit(scaladsl.ActorTestKit(name))
|
new ActorTestKit(scaladsl.ActorTestKit(name))
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a testkit named from the class that is calling this method,
|
||||||
|
* and use a custom config for the actor system.
|
||||||
|
*
|
||||||
|
* It will create an [[akka.actor.typed.ActorSystem]] with this name,
|
||||||
|
* e.g. threads will include the name.
|
||||||
|
* When the test has completed you should terminate the `ActorSystem` and
|
||||||
|
* the testkit with [[ActorTestKit#shutdownTestKit]].
|
||||||
|
*/
|
||||||
|
def create(customConfig: Config): ActorTestKit =
|
||||||
|
new ActorTestKit(scaladsl.ActorTestKit(TestKitUtils.testNameFromCallStack(classOf[ActorTestKit]), customConfig))
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create a named testkit, and use a custom config for the actor system.
|
* Create a named testkit, and use a custom config for the actor system.
|
||||||
*
|
*
|
||||||
|
|
@ -95,6 +115,11 @@ object ActorTestKit {
|
||||||
shutdown(system, settings.DefaultActorSystemShutdownTimeout.asJava, settings.ThrowOnShutdownTimeout)
|
shutdown(system, settings.DefaultActorSystemShutdownTimeout.asJava, settings.ThrowOnShutdownTimeout)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Config loaded from `application-test.conf`, which is used if no specific config is given.
|
||||||
|
*/
|
||||||
|
def applicationTestConfig: Config = scaladsl.ActorTestKit.ApplicationTestConfig
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
||||||
|
|
@ -39,9 +39,19 @@ import org.junit.rules.ExternalResource
|
||||||
* }
|
* }
|
||||||
* }
|
* }
|
||||||
* }}}
|
* }}}
|
||||||
|
*
|
||||||
|
* By default config is loaded from `application-test.conf` if that exists, otherwise
|
||||||
|
* using default configuration from the reference.conf resources that ship with the Akka libraries.
|
||||||
|
* The application.conf of your project is not used in this case.
|
||||||
|
* A specific configuration can be passed as constructor parameter.
|
||||||
*/
|
*/
|
||||||
final class TestKitJunitResource(_kit: ActorTestKit) extends ExternalResource {
|
final class TestKitJunitResource(_kit: ActorTestKit) extends ExternalResource {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Config loaded from `application-test.conf` if that exists, otherwise
|
||||||
|
* using default configuration from the reference.conf resources that ship with the Akka libraries.
|
||||||
|
* The application.conf of your project is not used in this case.
|
||||||
|
*/
|
||||||
def this() = this(ActorTestKit.create(TestKitUtils.testNameFromCallStack(classOf[TestKitJunitResource])))
|
def this() = this(ActorTestKit.create(TestKitUtils.testNameFromCallStack(classOf[TestKitJunitResource])))
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
||||||
|
|
@ -32,11 +32,15 @@ object ActorTestKit {
|
||||||
* e.g. threads will include the name.
|
* e.g. threads will include the name.
|
||||||
* When the test has completed you should terminate the `ActorSystem` and
|
* When the test has completed you should terminate the `ActorSystem` and
|
||||||
* the testkit with [[ActorTestKit#shutdownTestKit]].
|
* the testkit with [[ActorTestKit#shutdownTestKit]].
|
||||||
|
*
|
||||||
|
* Config loaded from `application-test.conf` if that exists, otherwise
|
||||||
|
* using default configuration from the reference.conf resources that ship with the Akka libraries.
|
||||||
|
* The application.conf of your project is not used in this case.
|
||||||
*/
|
*/
|
||||||
def apply(): ActorTestKit =
|
def apply(): ActorTestKit =
|
||||||
new ActorTestKit(
|
new ActorTestKit(
|
||||||
name = TestKitUtils.testNameFromCallStack(classOf[ActorTestKit]),
|
name = TestKitUtils.testNameFromCallStack(classOf[ActorTestKit]),
|
||||||
config = noConfigSet,
|
config = ApplicationTestConfig,
|
||||||
settings = None)
|
settings = None)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -46,9 +50,28 @@ object ActorTestKit {
|
||||||
* e.g. threads will include the name.
|
* e.g. threads will include the name.
|
||||||
* When the test has completed you should terminate the `ActorSystem` and
|
* When the test has completed you should terminate the `ActorSystem` and
|
||||||
* the testkit with [[ActorTestKit#shutdownTestKit]].
|
* the testkit with [[ActorTestKit#shutdownTestKit]].
|
||||||
|
*
|
||||||
|
* Config loaded from `application-test.conf` if that exists, otherwise
|
||||||
|
* using default configuration from the reference.conf resources that ship with the Akka libraries.
|
||||||
|
* The application.conf of your project is not used in this case.
|
||||||
*/
|
*/
|
||||||
def apply(name: String): ActorTestKit =
|
def apply(name: String): ActorTestKit =
|
||||||
new ActorTestKit(name = TestKitUtils.scrubActorSystemName(name), config = noConfigSet, settings = None)
|
new ActorTestKit(name = TestKitUtils.scrubActorSystemName(name), config = ApplicationTestConfig, settings = None)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create a testkit named from the class that is calling this method,
|
||||||
|
* and use a custom config for the actor system.
|
||||||
|
*
|
||||||
|
* It will create an [[akka.actor.typed.ActorSystem]] with this name,
|
||||||
|
* e.g. threads will include the name.
|
||||||
|
* When the test has completed you should terminate the `ActorSystem` and
|
||||||
|
* the testkit with [[ActorTestKit#shutdownTestKit]].
|
||||||
|
*/
|
||||||
|
def apply(customConfig: Config): ActorTestKit =
|
||||||
|
new ActorTestKit(
|
||||||
|
name = TestKitUtils.testNameFromCallStack(classOf[ActorTestKit]),
|
||||||
|
config = customConfig,
|
||||||
|
settings = None)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create a named testkit, and use a custom config for the actor system.
|
* Create a named testkit, and use a custom config for the actor system.
|
||||||
|
|
@ -89,9 +112,10 @@ object ActorTestKit {
|
||||||
def shutdown(system: ActorSystem[_], timeout: Duration, throwIfShutdownFails: Boolean = false): Unit =
|
def shutdown(system: ActorSystem[_], timeout: Duration, throwIfShutdownFails: Boolean = false): Unit =
|
||||||
TestKitUtils.shutdown(system, timeout, throwIfShutdownFails)
|
TestKitUtils.shutdown(system, timeout, throwIfShutdownFails)
|
||||||
|
|
||||||
// place holder for no custom config specified to avoid the boilerplate
|
/**
|
||||||
// of an option for config in the trait
|
* Config loaded from `application-test.conf`, which is used if no specific config is given.
|
||||||
private val noConfigSet = ConfigFactory.parseString("")
|
*/
|
||||||
|
val ApplicationTestConfig: Config = ConfigFactory.load("application-test")
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -116,8 +140,7 @@ final class ActorTestKit private[akka] (val name: String, val config: Config, se
|
||||||
* INTERNAL API
|
* INTERNAL API
|
||||||
*/
|
*/
|
||||||
@InternalApi private[akka] val internalSystem: ActorSystem[ActorTestKitGuardian.TestKitCommand] =
|
@InternalApi private[akka] val internalSystem: ActorSystem[ActorTestKitGuardian.TestKitCommand] =
|
||||||
if (config eq ActorTestKit.noConfigSet) ActorSystem(ActorTestKitGuardian.testKitGuardian, name)
|
ActorSystem(ActorTestKitGuardian.testKitGuardian, name, config)
|
||||||
else ActorSystem(ActorTestKitGuardian.testKitGuardian, name, config)
|
|
||||||
|
|
||||||
implicit def system: ActorSystem[Nothing] = internalSystem
|
implicit def system: ActorSystem[Nothing] = internalSystem
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -19,6 +19,11 @@ import org.scalatest.time.Span
|
||||||
*
|
*
|
||||||
* Note that ScalaTest is not provided as a transitive dependency of the testkit module but must be added explicitly
|
* Note that ScalaTest is not provided as a transitive dependency of the testkit module but must be added explicitly
|
||||||
* to your project to use this.
|
* to your project to use this.
|
||||||
|
*
|
||||||
|
* By default config is loaded from `application-test.conf` if that exists, otherwise
|
||||||
|
* using default configuration from the reference.conf resources that ship with the Akka libraries.
|
||||||
|
* The application.conf of your project is not used in this case.
|
||||||
|
* A specific configuration can be passed as constructor parameter.
|
||||||
*/
|
*/
|
||||||
abstract class ScalaTestWithActorTestKit(testKit: ActorTestKit)
|
abstract class ScalaTestWithActorTestKit(testKit: ActorTestKit)
|
||||||
extends ActorTestKitBase(testKit)
|
extends ActorTestKitBase(testKit)
|
||||||
|
|
@ -28,6 +33,11 @@ abstract class ScalaTestWithActorTestKit(testKit: ActorTestKit)
|
||||||
with ScalaFutures
|
with ScalaFutures
|
||||||
with Eventually {
|
with Eventually {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Config loaded from `application-test.conf` if that exists, otherwise
|
||||||
|
* using default configuration from the reference.conf resources that ship with the Akka libraries.
|
||||||
|
* The application.conf of your project is not used in this case.
|
||||||
|
*/
|
||||||
def this() = this(ActorTestKit(ActorTestKitBase.testNameFromCallStack()))
|
def this() = this(ActorTestKit(ActorTestKitBase.testNameFromCallStack()))
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,32 @@
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2019 Lightbend Inc. <https://www.lightbend.com>
|
||||||
|
*/
|
||||||
|
|
||||||
|
package jdocs.akka.actor.testkit.typed.javadsl;
|
||||||
|
|
||||||
|
// #default-application-conf
|
||||||
|
import com.typesafe.config.ConfigFactory;
|
||||||
|
|
||||||
|
// #default-application-conf
|
||||||
|
|
||||||
|
public class TestConfigExample {
|
||||||
|
|
||||||
|
void illustrateApplicationConfig() {
|
||||||
|
|
||||||
|
// #default-application-conf
|
||||||
|
ConfigFactory.load()
|
||||||
|
// #default-application-conf
|
||||||
|
;
|
||||||
|
|
||||||
|
// #parse-string
|
||||||
|
ConfigFactory.parseString("akka.loglevel = DEBUG \n" + "akka.log-config-on-start = on \n")
|
||||||
|
// #parse-string
|
||||||
|
;
|
||||||
|
|
||||||
|
// #fallback-application-conf
|
||||||
|
ConfigFactory.parseString("akka.loglevel = DEBUG \n" + "akka.log-config-on-start = on \n")
|
||||||
|
.withFallback(ConfigFactory.load())
|
||||||
|
// #fallback-application-conf
|
||||||
|
;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,2 @@
|
||||||
|
# used by ActorTestKitSpec
|
||||||
|
test.from-application-test = yes
|
||||||
|
|
@ -0,0 +1,2 @@
|
||||||
|
# used by ActorTestKitSpec
|
||||||
|
test.from-application = yes
|
||||||
|
|
@ -5,9 +5,10 @@
|
||||||
package akka.actor.testkit.typed.scaladsl
|
package akka.actor.testkit.typed.scaladsl
|
||||||
|
|
||||||
import akka.Done
|
import akka.Done
|
||||||
|
|
||||||
import scala.concurrent.Promise
|
import scala.concurrent.Promise
|
||||||
|
|
||||||
import akka.actor.typed.scaladsl.Behaviors
|
import akka.actor.typed.scaladsl.Behaviors
|
||||||
|
import com.typesafe.config.ConfigFactory
|
||||||
import org.scalatest.BeforeAndAfterAll
|
import org.scalatest.BeforeAndAfterAll
|
||||||
import org.scalatest.Matchers
|
import org.scalatest.Matchers
|
||||||
import org.scalatest.WordSpec
|
import org.scalatest.WordSpec
|
||||||
|
|
@ -62,6 +63,29 @@ class ActorTestKitSpec extends ScalaTestWithActorTestKit with WordSpecLike {
|
||||||
testkit2.shutdownTestKit()
|
testkit2.shutdownTestKit()
|
||||||
testkit2.system.whenTerminated.futureValue shouldBe a[Done]
|
testkit2.system.whenTerminated.futureValue shouldBe a[Done]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
"load application-test.conf by default" in {
|
||||||
|
testKit.config.getString("test.from-application-test") should ===("yes")
|
||||||
|
testKit.system.settings.config.getString("test.from-application-test") should ===("yes")
|
||||||
|
testKit.system.settings.config.hasPath("test.from-application") should ===(false)
|
||||||
|
}
|
||||||
|
|
||||||
|
"not load application-test.conf if specific Config given" in {
|
||||||
|
val testKit2 = ActorTestKit(ConfigFactory.parseString("test.specific-config = yes"))
|
||||||
|
testKit2.config.getString("test.specific-config") should ===("yes")
|
||||||
|
testKit2.system.settings.config.getString("test.specific-config") should ===("yes")
|
||||||
|
testKit2.config.hasPath("test.from-application-test") should ===(false)
|
||||||
|
testKit2.system.settings.config.hasPath("test.from-application-test") should ===(false)
|
||||||
|
testKit2.system.settings.config.hasPath("test.from-application") should ===(false)
|
||||||
|
|
||||||
|
// same if via ScalaTestWithActorTestKit
|
||||||
|
val scalaTestWithActorTestKit2 = new ScalaTestWithActorTestKit("test.specific-config = yes") {}
|
||||||
|
scalaTestWithActorTestKit2.testKit.config.getString("test.specific-config") should ===("yes")
|
||||||
|
scalaTestWithActorTestKit2.testKit.config.hasPath("test.from-application-test") should ===(false)
|
||||||
|
scalaTestWithActorTestKit2.system.settings.config.hasPath("test.from-application-test") should ===(false)
|
||||||
|
scalaTestWithActorTestKit2.testKit.system.settings.config.hasPath("test.from-application") should ===(false)
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,31 @@
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2019 Lightbend Inc. <https://www.lightbend.com>
|
||||||
|
*/
|
||||||
|
|
||||||
|
package docs.akka.actor.testkit.typed.scaladsl
|
||||||
|
|
||||||
|
object TestConfigExample {
|
||||||
|
|
||||||
|
def illustrateApplicationConfig(): Unit = {
|
||||||
|
|
||||||
|
//#default-application-conf
|
||||||
|
import com.typesafe.config.ConfigFactory
|
||||||
|
|
||||||
|
ConfigFactory.load()
|
||||||
|
//#default-application-conf
|
||||||
|
|
||||||
|
//#parse-string
|
||||||
|
ConfigFactory.parseString("""
|
||||||
|
akka.loglevel = DEBUG
|
||||||
|
akka.log-config-on-start = on
|
||||||
|
""")
|
||||||
|
//#parse-string
|
||||||
|
|
||||||
|
//#fallback-application-conf
|
||||||
|
ConfigFactory.parseString("""
|
||||||
|
akka.loglevel = DEBUG
|
||||||
|
akka.log-config-on-start = on
|
||||||
|
""").withFallback(ConfigFactory.load())
|
||||||
|
//#fallback-application-conf
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -58,7 +58,8 @@ to `application`—may be overridden using the `config.resource` property
|
||||||
If you are writing an Akka application, keep your configuration in
|
If you are writing an Akka application, keep your configuration in
|
||||||
`application.conf` at the root of the class path. If you are writing an
|
`application.conf` at the root of the class path. If you are writing an
|
||||||
Akka-based library, keep its configuration in `reference.conf` at the root
|
Akka-based library, keep its configuration in `reference.conf` at the root
|
||||||
of the JAR file.
|
of the JAR file. It's not supported to override a config property owned by
|
||||||
|
one library in a `reference.conf` of another library.
|
||||||
|
|
||||||
@@@
|
@@@
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -166,6 +166,50 @@ Scala
|
||||||
Java
|
Java
|
||||||
: @@snip [AsyncTestingExampleTest.java](/akka-actor-testkit-typed/src/test/java/jdocs/akka/actor/testkit/typed/javadsl/JunitIntegrationExampleTest.java) { #junit-integration }
|
: @@snip [AsyncTestingExampleTest.java](/akka-actor-testkit-typed/src/test/java/jdocs/akka/actor/testkit/typed/javadsl/JunitIntegrationExampleTest.java) { #junit-integration }
|
||||||
|
|
||||||
|
### Configuration
|
||||||
|
|
||||||
|
By default the `ActorTestKit` loads configuration from `application-test.conf` if that exists, otherwise
|
||||||
|
it is using default configuration from the reference.conf resources that ship with the Akka libraries. The
|
||||||
|
application.conf of your project is not used in this case.
|
||||||
|
A specific configuration can be given as parameter when creating the TestKit.
|
||||||
|
|
||||||
|
If you prefer to use `application.conf` you can pass that as the configuration parameter to the TestKit.
|
||||||
|
It's loaded with:
|
||||||
|
|
||||||
|
Scala
|
||||||
|
: @@snip [TestConfigExample.scala](/akka-actor-testkit-typed/src/test/scala/docs/akka/actor/testkit/typed/scaladsl/TestConfigExample.scala) { #default-application-conf }
|
||||||
|
|
||||||
|
Java
|
||||||
|
: @@snip [TestConfigExample.java](/akka-actor-testkit-typed/src/test/java/jdocs/akka/actor/testkit/typed/javadsl/TestConfigExample.java) { #default-application-conf }
|
||||||
|
|
||||||
|
It's often convenient to define configuration for a specific test as a `String` in the test itself and
|
||||||
|
use that as the configuration parameter to the TestKit. `ConfigFactory.parseString` can be used for that:
|
||||||
|
|
||||||
|
Scala
|
||||||
|
: @@snip [TestConfigExample.scala](/akka-actor-testkit-typed/src/test/scala/docs/akka/actor/testkit/typed/scaladsl/TestConfigExample.scala) { #parse-string }
|
||||||
|
|
||||||
|
Java
|
||||||
|
: @@snip [TestConfigExample.java](/akka-actor-testkit-typed/src/test/java/jdocs/akka/actor/testkit/typed/javadsl/TestConfigExample.java) { #parse-string }
|
||||||
|
|
||||||
|
Combining those approaches using `withFallback`:
|
||||||
|
|
||||||
|
Scala
|
||||||
|
: @@snip [TestConfigExample.scala](/akka-actor-testkit-typed/src/test/scala/docs/akka/actor/testkit/typed/scaladsl/TestConfigExample.scala) { #fallback-application-conf }
|
||||||
|
|
||||||
|
Java
|
||||||
|
: @@snip [TestConfigExample.java](/akka-actor-testkit-typed/src/test/java/jdocs/akka/actor/testkit/typed/javadsl/TestConfigExample.java) { #fallback-application-conf }
|
||||||
|
|
||||||
|
|
||||||
|
More information can be found in the [documentation of the configuration library](https://github.com/lightbend/config#using-the-library).
|
||||||
|
|
||||||
|
@@@ note
|
||||||
|
|
||||||
|
Note that `reference.conf` files are intended for libraries to define default values and shouldn't be used
|
||||||
|
in an application. It's not supported to override a config property owned by one library in a `reference.conf`
|
||||||
|
of another library.
|
||||||
|
|
||||||
|
@@@
|
||||||
|
|
||||||
### Controlling the scheduler
|
### Controlling the scheduler
|
||||||
|
|
||||||
It can be hard to reliably unit test specific scenario's when your actor relies on timing:
|
It can be hard to reliably unit test specific scenario's when your actor relies on timing:
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue