1

Helo, at the beginning i wold like to apologize for my english :)

akka=2.3.6
spray=1.3.2
scalatest=2.2.1

I encountered strange behavior of teting routes, which asks actors in handleWith directive,
I've route with handleWith directive

pathPrefix("firstPath") {
  pathEnd {
    get(complete("Hello from this api")) ~
    post(handleWith { (data: Data) =>{ println("receiving data") 
      (dataCalculator ? data).collect {
        case Success(_) =>
          Right(Created -> "")
        case throwable: MyInternalValidatationException =>
          Left(BadRequest -> s"""{"${throwable.subject}" : "${throwable.cause}"}""")
      }
    }})
  }
}


and simple actor wchich always responds when receive object Data and has own receive block wrapped in LoggingReceive, so I should see logs when message is receiving by actor

and i test it using (I think simple code)

class SampleStarngeTest extends WordSpec with ThisAppTestBase with OneInstancePerTest
with routeTestingSugar {
  val url = "/firstPath/"

  implicit val routeTestTimeout = RouteTestTimeout(5 seconds)

  def postTest(data: String) = Post(url).withJson(data) ~> routes

  "posting" should {
    "pass" when {
      "data is valid and comes from the identified user" in {
        postTest(correctData.copy(createdAt = System.currentTimeMillis()).asJson) ~> check {
          print(entity)
          status shouldBe Created
        }
      }
      "report is valid and comes from the anonymous" in {
        postTest(correctData.copy(createdAt = System.currentTimeMillis(), adid = "anonymous").asJson) ~> check {
          status shouldBe Created
        }
      }
    }
  }
}


and behavior:
When I run either all tests in package (using Intellij Idea 14 Ultimate) or sbt test I encounter the same results
one execution -> all tests pass
and next one -> not all pass, this which not pass I can see:
1. fail becouse Request was neither completed nor rejected within X seconds ( X up tp 60)
2. system console output from route from line post(handleWith { (data: Data) =>{ println("receiving data"), so code in handleWith was executed
3. ask timeout exception from route code, but not always (among failed tests)
4. no logs from actor LoggingReceive, so actor hasn't chance to respond
5. when I rerun teststhe results are even different from the previous

Is there problem with threading? or test modules, thread blocking inside libraries? or sth else? I've no idea why it isn't work :(

  • I don't think we have enough info to answer your question. Given that "receiving data" always appears on the console, it looks like something is going wrong with your dataCalculator actor. On an unrelated note, your .collect block is violating convention in its use of Either (see http://stackoverflow.com/questions/1193333/using-either-to-process-failures-in-scala-code). Generally speaking, Error conditions map to Left, and success conditions map to Right. This probably isn't the cause of your error, but will be confusing to others who read your code. – ffxtian Dec 01 '14 at 13:36
  • refactored in connection with ffxtian comment – user3416836 Dec 01 '14 at 15:37
  • Is it possible that you are not showing the correct code of test/route? Your route matches "firstPath" strictly with no slash at the end, but in your test you test for "firstPath/" with a trailing slash. But it should behave the same over different executions... Also, you may have issues related to the lack of "dynamic" directive, as you are matching request type without an extraction in the get case (http://spray.io/documentation/1.1-SNAPSHOT/spray-routing/execution-directives/dynamic/), which may lead to double responses or similar with random timings. – Diego Martinoia Dec 01 '14 at 17:29

0 Answers0