Giter VIP home page Giter VIP logo

scalatestplus-play's Introduction

ScalaTest Plus Play

Twitter Follow Discord GitHub Discussions StackOverflow YouTube Twitch Status OpenCollective

Build Status Maven Repository size Scala Steward badge Mergify Status

ScalaTest + Play provides integration support between ScalaTest and Play Framework.

Installation

To use it, please add the following dependency to your project's build.sbt or project/Build.scala file:

"org.scalatestplus.play" %% "scalatestplus-play" % "{VERSION}" % "test"

Where version is one of the listed below, according to your needs.

Releases

Release Play Scalatest Documentation
7.0.0 3.0.0 3.2.x docs
6.0.0 2.9.0 3.2.x docs
5.1.0 2.8.0 3.1.x docs
5.0.0 2.8.0 3.0.x docs
4.0.0 2.7.0 3.0.x docs
3.1.x 2.6.x 3.0.x docs
3.0.x 2.6.x 3.0.x docs
2.0.x 2.5.x 3.0.x docs
1.5.x 2.5.x 2.2.x docs
1.4.x 2.4.x 2.2.x docs
1.3.x 2.2.x 2.2.x docs

Contributions

See https://github.com/playframework/.github/blob/main/CONTRIBUTING.md

Releasing a new version

See https://github.com/playframework/.github/blob/main/RELEASING.md

License

ScalaTest Plus Play is licensed under the Apache license, version 2. See the LICENSE.txt file for more information.

scalatestplus-play's People

Contributors

aghmat avatar alexandervanhecke avatar billyautrey avatar bvenners avatar cheeseng avatar dasiu avatar dwijnand avatar ennru avatar fgrutsch avatar gacko avatar gheine avatar gmethvin avatar haukeh avatar ignasi35 avatar ihostage avatar jroper avatar marcospereira avatar markglh avatar mergify[bot] avatar mkurz avatar octonato avatar ptitficus avatar raboof avatar richdougherty avatar scala-steward avatar toshetah avatar uryyyyyyy avatar wsargent avatar xuwei-k avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

scalatestplus-play's Issues

Scala 2.11 support with Activator 2.3.6

build.sbt:

import play.core.PlayVersion.{current => playVersion}

lazy val root = (project in file(".")).enablePlugins(PlayScala)

scalaVersion := "2.11.4"

libraryDependencies ++= Seq(
  jdbc,
  anorm,
  cache,
  filters,
  "com.typesafe.play" %% "play"               % playVersion,
  "org.webjars"       %% "webjars-play"       % "2.3.0-2",
  "org.webjars"       %  "bootstrap"          % "3.1.1-2",
  "org.scalatestplus" %% "play"               % "1.0.0" % "test"
)
sbt.ResolveException: unresolved dependency: org.scalatestplus#play_2.11;1.0.0: not found

WithApplicationComponents causing java.lang.NoSuchMethodError

I'm using play 2.6.1 and scalatestplus-play 3.1.0

My test code looks roughly like

27: class CallbackControllerTest extends PlaySpec with OneAppPerSuiteWithComponents {
...
38: override def components: BuiltInComponentsFromContext = new BuiltInComponentsFromContext(context) with NoHttpFiltersComponents {
39:     import play.api.routing.Router
40:     lazy val router: Router = Router.empty
41:  }

At runtime I get

[info] com.ebay.n.bot.controllers.CallbackControllerTest *** ABORTED ***
[info]   java.lang.NoSuchMethodError: play.api.ApplicationLoader$.createContext$default$5()Lplay/api/inject/DefaultApplicationLifecycle;
[info]   at org.scalatestplus.play.components.WithApplicationComponents$class.context(WithApplicationComponents.scala:37)
[info]   at controllers.CallbackControllerTest.context$lzycompute(CallbackControllerTest.scala:27)
[info]   at controllers.CallbackControllerTest.context(CallbackControllerTest.scala:27)
[info]   at controllers.CallbackControllerTest$$anon$2.<init>(CallbackControllerTest.scala:38)
[info]   at controllers.CallbackControllerTest.components(CallbackControllerTest.scala:38)
[info]   at controllers.CallbackControllerTest.components(CallbackControllerTest.scala:27)
[info]   at org.scalatestplus.play.components.WithApplicationComponents$class.newApplication(WithApplicationComponents.scala:30)
[info]   at controllers.CallbackControllerTest.newApplication(CallbackControllerTest.scala:27)
[info]   at org.scalatestplus.play.components.OneAppPerSuiteWithComponents$class.fakeApplication(OneAppPerSuiteWithComponents.scala:141)
[info]   at controllers.CallbackControllerTest.fakeApplication(CallbackControllerTest.scala:27)

Am I doing something wrong? My goal is to obtain an instance of ControllerComponents so that I may test my compile-time DI Controllers.

Can not resolve/import "org.scalatestplus.play.guice.GuiceOneServerPerSuite"

Hi,

I want to use a fake application with custom configuration and need one server per suite (extends GuiceOneServerPerSuite)
It can not resolve/import org.scalatestplus.play.guice.GuiceOneServerPerSuite. I have following version in my build.sbt:

playVersion = "2.4.6"
ScalatestVersion = "3.0.0"
scalaTestPlus = 1.5.1"

Any idea what is the reason and what should I do?

Thanks

WsScalaTestClient referencing deprecated WSRequestHolder

I am trying to migrate to play framework 2.4 but I get the following compile error:

[error] missing or invalid dependency detected while loading class file 'WsScalaTestClient.class'.
[error] Could not access type WSRequestHolder in object play.api.libs.ws.WS,
[error] because it (or its dependencies) are missing. Check your build definition for
[error] missing or conflicting dependencies. (Re-run with `-Ylog-classpath` to see the problematic classpath.)
[error] A full rebuild may help if 'WsScalaTestClient.class' was compiled against an incompatible version of play.api.libs.ws.WS.
[error] one error found
[error] (test:compileIncremental) Compilation failed
[error] Total time: 8 s, completed Jul 20, 2015 4:50:07 PM

This is probably because of the following:
WSRequestHolder has been deprecated and renamed to WSRequest, see play 2.4.x migration guid.
To fix this:
WsScalaTestClient.class should reference the new WSRequest class.

Remove global state from tests and examples

There are a number of test that use WS.client or other examples of global mutable "Play.current" based state that will go away around Play 3.0.

This issue is to track removal of code and documentation that references global state.

No guidance on how to access components for running application

Currently there's no built-in way to access the components actually used by the running application for a given test, and there's not really any guidance on how to do so manually. You can use components, but that will create new instances rather than using the existing one. It doesn't make sense to use the injector of the current application because it's not populated for compile-time DI apps. See also playframework/playframework#8099.

One way to solve the problem is to use a trait like this to satisfy the components dependency:

trait WithComponents[C <: BuiltInComponents] extends WithApplicationComponents {
  private var _components: C = null

  // Override this to customize how new components are created.
  def newComponents: C

  // This method is used to access the current components inside a test.
  final def currentComponents: C =
    if (_components eq null) sys.error("Components not defined!") else _components

  // This method is called once when creating an application.
  // Use currentComponents to access the components inside a test.
  final def components: BuiltInComponents = {
    _components = newComponents
    _components
  }
}

While it's possible to do this yourself, it doesn't feel very obvious so I think it would be useful to add a helper like this to the library, or change the WithApplicationComponents to work like this.

Part of the problem is also that we're using variables at the class level to store the application, rather than doing all this in a local scope. This also means it doesn't make sense to run tests in the same class in parallel, because they share this state. So we may also want to recommend a local test scope for each test rather than having it automatically provided by the testing traits, something like WithApplication in play-specs2.

app implicit is null in GuiceOneAppPerTest

Hi Scalatest team,

I seem to have the issue that the app implicit is null when using the GuiceOneAppPerTest trait for testing. When I use GuiceOneAppPerSuite it is fine. I discovered this when investigating why my dependency injection in the test did not work as expected: Link

Scala version 2.12.3, play 2.6.3 and scalatestplus-play 3.1.2.

To reproduce:

  • Create a new play project: sbt new playframework/play-scala-seed.g8
  • Add a simple println into the test which uses GuiceOneAppPerTest: println("App object", app)

Expected result: app is defined
Actual result: app is null

If you could please investigate that is is really an issue or wrong use from my end or the g8 template. Thank you very much for this great framework!

It seems that if afterAll method contains a value depends on application, then it won't run.

I've written a test with OneAppPerSuite and BeforeAndAfterAll. It looks like below:

class TestSpec extends FreeSpec with MustMatchers with OneAppPerSuite with PropertyChecks with ScalaFutures with BeforeAndAfter {
  lazy val testDao = app.injector.instanceOf[TestDao]

  override def afterAll() = {
    await(testDao.deleteById(testId))
  }
}

When code runs to afterAll, it will throw exception. I think it maybe due to that application is already stopped. So testDao can't get any resource from database connection pool. I'm wondering if this can be fixed or I have to clean data with after method.

Got empty body while send fake post request to controller

Play: 2.6.0-M5

ScalaTestPlus: 3.0.0-RC1

def post = Action(parse.json) { implicit request =>
    Ok(request.body)
  }
implicit val system = ActorSystem()
implicit val materializer = ActorMaterializer()
 "post json" in {
      val fake = FakeRequest()
        .withMethod("post")
        .withHeaders("Content-Type" -> "application/json")
        .withRawBody(jsonByte)
      val result = controller.post.apply(fake)
      val resultText = contentAsString(result)
      resultText mustEqual("true")
    }

I make a fake json request and invoke it with the action.apply
Those leads to

Invalid Json: No content to map due to end-of-input
[info]    at [Source: akka.util.ByteIterator$ByteArrayIterator$$anon$1@4d7733b; line: 1, column: 0]

I thought it may relate to actorSytem and materializer I use.

Do you guys know how could I post the request correctly?

Update the Versions, Versions, Versions page

Currently, the Versions, Versions, Versions page lists the correct version of scalatestplus-play to use -- but the links to the ScalaDocs are messed up. Specifically, all of the versions point to the 1.0.0 docs! I just lost a fair while trying to figure out why my tests weren't working after upgrading to Play 2.4; eventually I realized it was because I was looking an antique and out-of-date Scaladoc, which didn't match the version 1.4.0 that I was actually using.

I'm now working around this by reading the Scaladoc comments directly in the source code, but it would help the community if these links got fixed...

Revamp Travis build

This travis build currently has 4 jobs ran over a copatibility matrix of 4 cells totalling 16 jobs.

Something this big sometimes clogs the build queue.

Considering the fixed cost of setting up the VM, installing dependencies and starting sbt I think we should collpase the 4 jobs into only 2 or even a single job sbt "do all the things" until we shrink the compatibility matrix.

Doesn't seem like the JVM arguments make their way into the Application.

When trying to run the test using GuiceOneAppPerSuite doesn't seem like the JVM arguments set in Build.scala are being passed into the Application instance of the JVM.


         implicit val ec = scala.concurrent.ExecutionContext.global
         val cc = Helpers.stubControllerComponents()

         val controller = new Model(cc, new Authenticated(cc.parsers.defaultBodyParser))
         val result: Future[Result] = controller.getPage(1L).apply(FakeRequest())

Can't Use BeforeAndAfterAll Because Play is Stopped

I'm trying to use BeforeAndAfterAll and an afterall to cleanup some stuff. But by the time afterall gets called, Play has already shutdown. In BaseOneAppPerSuite it does this:

val status = super.run(testName, newArgs)
status.whenCompleted { _ => Play.stop(app) }

Which runs before the afterall.

[Question] OneBrowserPerSuite: How to prevent browser startup when skipping tests using this trait?

I'm in a scenario where unittests and fluentlenium integration tests are placed in the same module but need to be run seperately at different stages of deployment in different environments.

A Fluentlenium Spec might look like this

@IntegrationTest
class IntegrationSpec extends WordSpec with MustMatchers  with GuiceOneServerPerSuite with OneBrowserPerSuite {
 override def fakeApplication(): Application = FluentleniumSetup.app
 override def createWebDriver(): WebDriver = FluentleniumSetup.createWebDriver()
...
}

and a unit test like this

@UnitTest
class FooSpec extends WordSpec with MustMatchers with TypeCheckedTripleEquals {
...
}

To be able to seperate the test executions, this configuration in build.sbt was created:

lazy val ITest = config("i").extend(Test)
lazy val UTest = config("u").extend(Test)
testOptions in ITest += Tests.Argument(TestFrameworks.ScalaTest, "-l","foo.bar.UnitTest
testOptions in UTest += Tests.Argument(TestFrameworks.ScalaTest, "-l","foo.bar.IntegrationTest")

This way i can run sbt u:test and all suits annotated with @IntegrationTest will be skipped due to the exclude flag -l.
But still, whenever test execution reaches a Test annotated with IntegrationSpec, a browser gets started and closes immediately without doing anything, because all tests in this Suite get skipped. Since there is no browser installed in the environment where u:test is meant to be executed, this attempt to start a browser breaks test execution. Which is unfortunate because it wouldn't be necessary to start a browser at all. Am i doing something wrong in my attempt to skip the Testsuits?

Errors on 3.0.0-RC1

Tried RC1 on a simple repository with two tests

"Index controller" should {
    "return valid response" in {
      val controller = new IndexController()

      val result = controller.index().apply(FakeRequest())
      val bodyText = Helpers.contentAsString(result)
      bodyText should include ("<script src=\"/assets/client-opt.js\" type=\"text/javascript\"></script>")
    }
  }
"GET /" should {
    "return result" in {
      val Some(f) = route(app, FakeRequest(GET, "/"))

      ScalaFutures.whenReady(f) { result =>
        result.header.status mustBe OK
      }
    }
  }

And are seeing some strange errors

[info] controllers.IndexControllerTest *** ABORTED ***
[info]   java.lang.AbstractMethodError:
[info]   at play.api.mvc.Results$class.$init$(Results.scala:490)
[info]   at controllers.IndexController.<init>(IndexController.scala:5)
[info]   at controllers.IndexControllerTest$$anonfun$1$$anonfun$apply$mcV$sp$1.apply(IndexControllerTest.scala:13)
[info]   at controllers.IndexControllerTest$$anonfun$1$$anonfun$apply$mcV$sp$1.apply(IndexControllerTest.scala:12)
[info]   at org.scalatest.OutcomeOf$class.outcomeOf(OutcomeOf.scala:85)
[info]   at org.scalatest.OutcomeOf$.outcomeOf(OutcomeOf.scala:104)
[info]   at org.scalatest.Transformer.apply(Transformer.scala:22)
[info]   at org.scalatest.Transformer.apply(Transformer.scala:20)
[info]   at org.scalatest.WordSpecLike$$anon$1.apply(WordSpecLike.scala:1078)
[info]   at org.scalatest.TestSuite$class.withFixture(TestSuite.scala:196)

Hope this helps.

Update Scalatest references

Problems testing DAO objects through the test framework

We are using latest stable of scalatestplus-play in our project and quite happy with this. All tests build locally but when we move over to travis where we have to override timeouts to be able to run the tests the problem starts.

Travis specific configuration for running h2database in slick with OneAppPerSuite trait:

def inMemoryDatabaseConfig(evolve:String = "enabled"):Map[String, Any] = Map.apply (
    "slick.dbs.default.driver" -> "slick.driver.H2Driver$",
    "slick.dbs.default.connectionTimeout" -> "20000",
    "slick.dbs.default.loginTimeout" -> "20000",
    "slick.dbs.default.socketTimeout" -> "20000",
    "slick.dbs.default.db.driver" -> "org.h2.Driver",
    "slick.dbs.default.connectionTestQuery" -> "SELECT 1",
    "slick.dbs.default.db.url" -> "jdbc:h2:mem:play-test",
    "slick.dbs.default.leakDetectionThreshold" -> "5000",
    "evolutionplugin" -> evolve
  )

When overriding the application for OneAppPerSuite trait in the test with:

implicit override lazy val app = new GuiceApplicationBuilder().configure(PlayTestDefaults.inMemoryDatabaseConfig()).build()

We keep getting random timeouts around 1 seconds when running in Travis CI:
[info] - com.zaxxer.hikari.HikariDataSource - HikariCP pool db is starting.
[info] Exception encountered when attempting to run a suite with class name: ActorUnitTest *** ABORTED ***
[info]   java.sql.SQLTimeoutException: Timeout after 1000ms of waiting for a connection.
[info]   at com.zaxxer.hikari.pool.BaseHikariPool.getConnection(BaseHikariPool.java:227)
[info]   at com.zaxxer.hikari.pool.BaseHikariPool.getConnection(BaseHikariPool.java:182)
[info]   at com.zaxxer.hikari.HikariDataSource.getConnection(HikariDataSource.java:93)
[info]   at slick.jdbc.hikaricp.HikariCPJdbcDataSource.createConnection(HikariCPJdbcDataSource.scala:12)
[info]   at play.api.db.slick.evolutions.internal.DBApiAdapter$DatabaseAdapter.getConnection(DBApiAdapter.scala:57)
[info]   at play.api.db.slick.evolutions.internal.DBApiAdapter$DatabaseAdapter.getConnection(DBApiAdapter.scala:60)
[info]   at play.api.db.evolutions.DatabaseEvolutions.databaseEvolutions(EvolutionsApi.scala:119)
[info]   at play.api.db.evolutions.DatabaseEvolutions.scripts(EvolutionsApi.scala:97)
[info]   at play.api.db.evolutions.DatabaseEvolutions.scripts(EvolutionsApi.scala:112)
[info]   at play.api.db.evolutions.DefaultEvolutionsApi.scripts(EvolutionsApi.scala:77)
[info]   ...

Typical travis output: https://travis-ci.org/MUSIT-Norway/musit/builds/127490303

Project url: https://github.com/MUSIT-Norway/musit
The integration tests are not run in Travis CI so they are fine, but the unit tests are, all service_* sub projects are microservices running with a singular Playframework instance so the tests are contained there.

Not sure why this is happening, but it seems to be PlaySpec OneAppPerSuite not closing connections fast enough so the tests are able to run through. And we cant seem to set the timeouts to override the defaults.

Update readme to explain Play version compatibility

I noticed a lot of people on the play mailing list are confused when they upgrade their app and their tests suddenly break. It would be helpful if the readme clearly explained which version they are supposed to be using for each version of Play.

Success of before and after injection varies according to GuiceOneServerPerTest or GuiceOneServerPerSuite

So the below with GuiceOneServerPerSuite is fine but switching that to GuiceOneServerPerTest means the application is null in beforeAll():

import org.scalatest.BeforeAndAfterEach
import org.scalatestplus.play._
import org.scalatestplus.play.guice._
import play.api.Configuration
import play.api.test.Injecting

class BeforeAndAfter extends PlaySpec with Injecting with GuiceOneServerPerSuite with
  BeforeAndAfterEach {

  "How do I get dependencies in before and after" should {
    "2 + 2 = 4" in{
      assert((2+2) ==  4)
      val playConfig = inject[Configuration]
      println(playConfig)
    }

  }

  override protected def beforeEach(): Unit = {
    val playConfig = inject[Configuration]
    println(playConfig)
  }

  override protected def afterEach(): Unit = {
    val playConfig = inject[Configuration]
    println(playConfig)
  }
}

But the below fails with a null pointer in beforeEach:

**Exception encountered when invoking run on a nested suite.
java.lang.NullPointerException
	at play.api.test.Injecting.inject(Helpers.scala:631)
	at play.api.test.Injecting.inject$(Helpers.scala:630)
	at BeforeAndAfter.inject(BeforeAndAfter.scala:7)
	at BeforeAndAfter.beforeEach(BeforeAndAfter.scala:22)**
import org.scalatest.BeforeAndAfterEach
import org.scalatestplus.play._
import org.scalatestplus.play.guice._
import play.api.Configuration
import play.api.test.Injecting

class BeforeAndAfter extends PlaySpec with Injecting with GuiceOneServerPerTest with
  BeforeAndAfterEach {

  "How do I get dependencies in before and after" should {
    "2 + 2 = 4" in{
      assert((2+2) ==  4)
      val playConfig = inject[Configuration]
      println(playConfig)
    }

  }


  //runs fine if below commented out
  override protected def beforeEach(): Unit = {
    val playConfig = inject[Configuration]
    println(playConfig)
  }

  override protected def afterEach(): Unit = {
    val playConfig = inject[Configuration]
    println(playConfig)
  }
}

Use GuiceOneAppPerSuite with async tests

I have a async test suite that extends AsyncFunSpec.

Now, it seems to be not possible to also mix-in GuiceOneAppPerSuite:

// does not work
class PostSpec extends AsyncFunSpec with GuiceOneAppPerSuite with Matchers {
  it("returns posts") {
    val repo = app.injector.instanceOf[PostRepository]

    repo.create("my post").map { _ =>
      val request = FakeRequest(GET, "/posts")
      val result = route(app, request).get

      status(result) shouldEqual OK
      contentAsJson(result).as[JsArray].value.size shouldEqual 1
    }
  }
}

I am no scala magician, but I figure this is because GuiceOneAppPerSuite demands TestSuite while AsyncFunSpec inherits from AsyncTestSuite.

I figure an easy workaround would be to have an (otherwise identical) GuiceOneAppPerSuiteAsync that uses the AsyncTestSuite inheritance tree as follows:

/*
 * Copyright 2001-2016 Artima, Inc.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

// this is an adjusted version of
// https://github.com/playframework/scalatestplus-play/blob/master/module/src/main/scala/org/scalatestplus/play/BaseOneAppPerSuite.scala
package org.scalatestplus.play

import org.scalatest.{Args, AsyncTestSuite, AsyncTestSuiteMixin, Status}
import org.scalatestplus.play.FakeApplicationFactory
import play.api.{Application, Play}

/**
  * The base abstract trait for one app per suite.
  */
trait BaseOneAppPerSuiteAsync extends AsyncTestSuiteMixin { this: AsyncTestSuite with FakeApplicationFactory =>

  /**
    * An implicit instance of `Application`.
    */
  implicit lazy val app: Application = fakeApplication()

  /**
    * Invokes `Play.start`, passing in the `Application` provided by `app`, and places
    * that same `Application` into the `ConfigMap` under the key `org.scalatestplus.play.app` to make it available
    * to nested suites; calls `super.run`; and lastly ensures `Play.stop` is invoked after all tests and nested suites have completed.
    *
    * @param testName an optional name of one test to run. If `None`, all relevant tests should be run.
    *                 I.e., `None` acts like a wildcard that means run all relevant tests in this `Suite`.
    * @param args the `Args` for this run
    * @return a `Status` object that indicates when all tests and nested suites started by this method have completed, and whether or not a failure occurred.
    */
  abstract override def run(testName: Option[String], args: Args): Status = {
    Play.start(app)
    try {
      val newConfigMap = args.configMap + ("org.scalatestplus.play.app" -> app)
      val newArgs = args.copy(configMap = newConfigMap)
      val status = super.run(testName, newArgs)
      status.whenCompleted { _ => Play.stop(app) }
      status
    } catch { // In case the suite aborts, ensure the app is stopped
      case ex: Throwable =>
        Play.stop(app)
        throw ex
    }
  }
}

trait GuiceOneAppPerSuiteAsync extends scala.AnyRef with BaseOneAppPerSuiteAsync with org.scalatestplus.play.guice.GuiceFakeApplicationFactory {
  this : GuiceOneAppPerSuiteAsync with org.scalatest.AsyncTestSuite =>
}

Is there an easier way? And if not, should I create a pull request to add these traits?

PhantomJS integration?

Hello!
Great work on an awesome framework.

I was wondering if there were plans to make a Factory equivalent for PhantomJS to run headless browser tests.

If not, any advice on integrating that with the existing scalatestplus framework would be nice in the meanwhile.

Cheers

4.0.1 JAR on Maven Central has malformed META-INF/MANIFEST.M

I was having trouble using the edit 4.0.1 JAR.

I downloaded it and cracked it open.

curl -O -L http://central.maven.org/maven2/org/scalatestplus/play/scalatestplus-play_2.12/4.0.1/scalatestplus-play_2.12-4.0.1.jar
tar -xf scalatestplus-play_2.12-4.0.1.jar
cat META-INF/MANIFEST.MF

Looks like an extra newline got inserted into the Implementation-URL field.

Manifest-Version: 1.0
Implementation-Title: scalatestplus-play
Implementation-Version: 4.0.1
Specification-Vendor: org.scalatestplus.play
Specification-Title: scalatestplus-play
Implementation-Vendor-Id: org.scalatestplus.play
Specification-Version: 4.0.1
Implementation-URL: https://github.com/playframework/scalatestplus-pla
 y
Implementation-Vendor: org.scalatestplus.play

Release for scalatest 2.2

Please release scalatestplus-play for scalatest 2.2.

We get a SBT error for this combination of dependencies:

  • "org.scalatest" %% "scalatest" % "2.2.0" % "test"
  • "org.scalatestplus" %% "play" % "1.1.0" % "test"
Exception in thread "Thread-32" java.io.EOFException
    at java.io.ObjectInputStream$BlockDataInputStream.peekByte(ObjectInputStream.java:2601)
    at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1319)
    at java.io.ObjectInputStream.readObject(ObjectInputStream.java:371)
    at sbt.React.react(ForkTests.scala:117)
    at sbt.ForkTests$$anonfun$mainTestTask$1$Acceptor$2$.run(ForkTests.scala:76)
    at java.lang.Thread.run(Thread.java:744)
sbt.ForkMain$ForkError: org/scalautils/Tolerance
    at java.lang.Class.forName0(Native Method)
    at java.lang.Class.forName(Class.java:340)
    at org.scalatest.tools.Framework$ScalaTestTask.loadSuiteClass(Framework.scala:606)
    at org.scalatest.tools.Framework$ScalaTestTask.suiteClass$lzycompute(Framework.scala:614)
    at org.scalatest.tools.Framework$ScalaTestTask.suiteClass(Framework.scala:614)
    at org.scalatest.tools.Framework$ScalaTestTask.accessible$lzycompute(Framework.scala:615)
    at org.scalatest.tools.Framework$ScalaTestTask.accessible(Framework.scala:615)
    at org.scalatest.tools.Framework$ScalaTestTask.shouldDiscover$lzycompute(Framework.scala:618)
    at org.scalatest.tools.Framework$ScalaTestTask.shouldDiscover(Framework.scala:617)
    at org.scalatest.tools.Framework$ScalaTestRunner$$anonfun$tasks$2.apply(Framework.scala:875)
    at org.scalatest.tools.Framework$ScalaTestRunner$$anonfun$tasks$2.apply(Framework.scala:873)
    at scala.collection.TraversableLike$WithFilter$$anonfun$map$2.apply(TraversableLike.scala:722)
    at scala.collection.IndexedSeqOptimized$class.foreach(IndexedSeqOptimized.scala:33)
    at scala.collection.mutable.ArrayOps$ofRef.foreach(ArrayOps.scala:108)
    at scala.collection.TraversableLike$WithFilter.map(TraversableLike.scala:721)
    at org.scalatest.tools.Framework$ScalaTestRunner.tasks(Framework.scala:873)
    at sbt.ForkMain$Run.runTests(ForkMain.java:251)
    at sbt.ForkMain$Run.run(ForkMain.java:137)
    at sbt.ForkMain.main(ForkMain.java:119)
Caused by: sbt.ForkMain$ForkError: org.scalautils.Tolerance
    at java.net.URLClassLoader$1.run(URLClassLoader.java:372)
    at java.net.URLClassLoader$1.run(URLClassLoader.java:361)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.net.URLClassLoader.findClass(URLClassLoader.java:360)
    at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
    at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:308)
    at java.lang.ClassLoader.loadClass(ClassLoader.java:357)
    at java.lang.Class.forName0(Native Method)
    at java.lang.Class.forName(Class.java:340)
    at org.scalatest.tools.Framework$ScalaTestTask.loadSuiteClass(Framework.scala:606)
    at org.scalatest.tools.Framework$ScalaTestTask.suiteClass$lzycompute(Framework.scala:614)
    at org.scalatest.tools.Framework$ScalaTestTask.suiteClass(Framework.scala:614)
    at org.scalatest.tools.Framework$ScalaTestTask.accessible$lzycompute(Framework.scala:615)
    at org.scalatest.tools.Framework$ScalaTestTask.accessible(Framework.scala:615)
    at org.scalatest.tools.Framework$ScalaTestTask.shouldDiscover$lzycompute(Framework.scala:618)
    at org.scalatest.tools.Framework$ScalaTestTask.shouldDiscover(Framework.scala:617)
    at org.scalatest.tools.Framework$ScalaTestRunner$$anonfun$tasks$2.apply(Framework.scala:875)
    at org.scalatest.tools.Framework$ScalaTestRunner$$anonfun$tasks$2.apply(Framework.scala:873)
    at scala.collection.TraversableLike$WithFilter$$anonfun$map$2.apply(TraversableLike.scala:722)
    at scala.collection.IndexedSeqOptimized$class.foreach(IndexedSeqOptimized.scala:33)
    at scala.collection.mutable.ArrayOps$ofRef.foreach(ArrayOps.scala:108)
    at scala.collection.TraversableLike$WithFilter.map(TraversableLike.scala:721)
    at org.scalatest.tools.Framework$ScalaTestRunner.tasks(Framework.scala:873)
    at sbt.ForkMain$Run.runTests(ForkMain.java:251)
    at sbt.ForkMain$Run.run(ForkMain.java:137)
    at sbt.ForkMain.main(ForkMain.java:119)

deprecated WebBrowser is used

OneBrowserPerSuite (and other classes) use the deprecated selenium.WebBrowser class instead of the new org.scalatestplus.selenium.WebBrowser. Since I'm using the -Xfatal-warnings flag, I'm forced to upgrade my tests using selenium.WebBrowser to org.scalatestplus.selenium.WebBrowser. But tests also inheriting from OneBrowserPerSuite now have conflicting definitions of WebBrowser, which introduces another compliation error.

will provide a pull request.

ScalaTest 3.0 Support

Currently I think it would be great if we would get ScalaTest 3.0 support.
I also don't think that Play-2.5 will be released before ScalaTest 3.0 is released.

Support using custom ApplicationLoader in addition to FakeApplication

With Play 2.4 it seems to me that it will be more common to use a custom application loader now to define your dependencies for your tests, etc than it will be to use a FakeApplication type.

The specs2 support built-in in play provides this via this helper:
https://github.com/playframework/playframework/blob/master/framework/src/play-specs2/src/main/scala/play/api/test/Specs.scala#L25-L30

This becomes very handy when trying to use compile time DI with play 2.4 This sample product using specs2 shows how nice this can be: https://github.com/loicdescotte/play24SimpleDI

I would love to be able to do the same in using ScalaTest as we move our project DI to compile time.

Perhaps this is already possible on the milestone and I'm just missing it? I'd like to be able to use a custom ApplicationLoader on something like OneAppPerSuite for example.

Release new version

Any ETA on when a new version with the ScalaTest 3 changes will be released?

Add test suites and options for compile time dependency injection

ScalaTest Plus uses GuiceApplicationBuilder as the default Application if none is defined, as the default argument.

Ideally this functionality should be broken out so that users who are leveraging a compile time DI framework as an application builder can leverage classes without having to reimplement code.

There's a sample project here that shows equivalent compile time DI tests using manual compile time DI. It's not hard, but you have to know the source code and where the app is being created before you can get started writing tests.

https://github.com/playframework/play-scala-compile-di-with-tests

Routes not loading

Based on the examples in the docs, and the tests provided with the scala play starter project, I wrote a couple tests for a new app. Unexpectedly, the requests I make in my tests come back as 404s. I'm wondering if there's some special step I need to take to ensure the routes are compiled for tests?

Here are the tests... maybe I'm missing something obvious:

import org.scalatestplus.play._
import org.scalatestplus.play.guice.GuiceOneAppPerSuite
import play.api.test._
import play.api.test.Helpers._
import play.api.libs.json.Json


class Routes extends PlaySpec with GuiceOneAppPerSuite {

  "Shotgun Routes" should {
    "find_one should be able to find onelson" in  {
      val req = FakeRequest(POST, "/sg/relay/find_one")
        .withJsonBody(Json.parse("""{"kwargs":{"entity_type":"HumanUser","filters":[["login","is","onelson"]]}}"""))
      val resp = route(app, req).get
      status(resp) mustBe OK
      contentType(resp) mustBe Some("application/json")
      (contentAsJson(resp) \ "id").as[Int] mustBe 948
    }
  }

  "DSE Routes" should {
    "graph vert labels should be able OK" in  {
      val req = FakeRequest(GET, "/dse/graph/vert-labels")
      val resp = route(app, req).get
      status(resp) mustBe OK
      contentType(resp) mustBe Some("application/json")
      contentAsString(resp) must include ("Asset")
    }
  }

}

The requests, as written, should match what I have in my routes file, and the app is working when I push requests to it in practice.

POST    /sg/relay/:methodName    controllers.RelayController.run(methodName: String)
GET     /dse/:graph/vert-labels      controllers.AtlasLegacyController.vertLabels(graph: String)
POST    /dse/:graph/gremlin          controllers.AtlasLegacyController.gremlin(graph: String)

Is there something missing?

I'm running Play 2.5.15, with scalatestplus-play 2.0.0.

Thanks,
Owen

MixedPlaySpec runs tests in Parallel

This was originally reported in the following playframework PR:

playframework/playframework#5514

It was reported that MixedPlaySpec runs its tests parallel unexpectedly.

Here's the examples given by @schmitch:

This one will keep my database connections at a peek of 21:

class AppDoubleSpec extends PlaySpec with OneAppPerTest{

  var mutSeq = mutable.ListBuffer[String]()

  "Blabla" should {
    "be only happen once first" in {
      mutSeq.length must be(0)
    }
    "be only happen once second" in {
      mutSeq += "hello world"
      mutSeq.length must be(1)
    }
    "be only happen once third" in {
      mutSeq.length must be(1)
    }
  }

  "Blabla2" should {
    "be only happen once" in {
      mutSeq.length must be(1)
    }
  }

}

This one will peek my connections to 84:

class AppDoubleSpec extends MixedPlaySpec {

  var mutSeq = mutable.ListBuffer[String]()

  "Blabla" should {
    "be only happen once first" in new App {
      mutSeq.length must be(0)
    }
    "be only happen once second" in new App {
      mutSeq += "hello world"
      mutSeq.length must be(1)
    }
    "be only happen once third" in new App {
      mutSeq.length must be(1)
    }
  }

  "Blabla2" should {
    "be only happen once" in new App {
      mutSeq.length must be(1)
    }
  }

}

and he is using the following python script to look at the opened connection:

import psycopg2

conn = psycopg2.connect("dbname=loki user=loki password=loki")
conn.autocommit = True

last = None
with conn:
    with conn.cursor() as cur:
        while True:

            ret = cur.execute("SELECT sum(numbackends) FROM pg_stat_database;")
            current = cur.fetchone()[0] - 1

            if current != last and current - 1 != last:
                print(current)

            last = current

conn.close()

and @bvenners mentioned this:

The one difference I can see is that we are still using FakeApplication in MixedFixtures, but are using GuicrApplicationBuilder on OneSppPerTest. That's unintended anyway because we thought we'd completely switched over to GuiceApplicationBuilder. We'll fix that, but I'd like to try and reproduce your issue. How are you counting your database connections? (Probably we should move this to a ScalaTest+Play issue.)

OneAppPerSuite throws ClassCastException

scalatestplus-play version: 1.5.1 (also tested with 1.5.0)
play version: 2.5.2
scala: 2.11.8
sbt: 0.13.11

I have a test that mixes in OneAppPerSuite, starts an application and then runs some tests. All of the tests pass but after they have completed, the suite fails with an exception that is thrown from inside scalatestplus-play. The stacktrace:

[info]   java.lang.ClassCastException: scala.util.Success cannot be cast to java.lang.Boolean
[info]   at scala.runtime.BoxesRunTime.unboxToBoolean(BoxesRunTime.java:85)
[info]   at org.scalatestplus.play.OneAppPerSuite$$anonfun$run$1.apply(OneAppPerSuite.scala:144)
[info]   at org.scalatest.CompositeStatus.whenCompleted(Status.scala:891)
[info]   at org.scalatestplus.play.OneAppPerSuite$class.run(OneAppPerSuite.scala:144)

I've walked through the code in OneAppPerSuite and CompositeStatus and I can't see anything obviously wrong.

Use Application instead of FakeApplication

In Play 2.4, it is very easy to create Application instances for test using GuiceApplicationBuilder. At the same time, FakeApplication has several constraints on the objects it can create (for example, it can't override Guice modules).

Now, that FakeApplication extends Application, it would be better to use Application in traits like OneAppPerTest.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.