2013-10-07 9 views
0

Моя пьеса приложение использует AKKA актера для обработки длительных вычислений:Тестирование играть взаимодействие контроллера с AKKA актера

class MyController(myActor : ActorRef) extends Controller{ 
    def doStuff = Action { implicit request => 

    val response : Future[Any] = myActor ? DoStuff 

    Async{ 
     response.map{   
     str : String => Ok(str) 
     } 
    } 
    } 
} 

Я пытаюсь проверить, что все работает должным образом. У меня есть отдельные тесты для проверки того, что актер ведет себя правильно и в основном просто хочет проверить, что контроллер отправляет правильные сообщения пользователю. Мой текущий подход вроде этого:

class MyControllerSpec extends Specification{ 
    "MyController" should { 

    object DummyActor extends Actor{ 
     def receive = { 
     case _ =>() 
     } 
    } 

    "do stuff properly" >> { 
     val probe = TestProbe()(Akka.system) 
     val test = new controllers.MyController(Akka.system.actorOf(Props(DummyActor)) 
     val result = test.doStuff(FakeRequest()) 
     probe.expectMsg(SomeMsg) 
    } 
    } 
} 

Контроллера посылает сообщение переданных в актере, когда действие DoStuff называется. Я пытаюсь проверить, отправлен ли правильный msg.

Я думаю, что test.doStuff запускается синхронно и время, когда фиктивный актер ничего не посылает. ОжиданиеMsg не запускается до тех пор, пока не будет возвращен вызов doStuff и уже отправлен SomeMsg. Как я могу решить эту проблему?

ответ

1

Это не то, что вы хотите передать зонд своему контроллеру, а не реализацию фиктивного актера, как бы что-то было отправлено на зонд, если нет?

+0

Вы правы. Я ошибся при изменении своего кода, чтобы использовать зонд вместо специального актера. Фиктивный актер даже не нужен. Тест теперь работает. Я хотел бы принять ваш ответ, но было бы здорово, если бы вы могли дать более подробное объяснение, почему это работает. Действительно ли вызов doStuff выполняется асинхронно, в отличие от того, что я сказал в вопросе? Может ли этот тест выйти из строя, если сообщение msg будет отправлено в ближайшее время? Благодарю. – mushroom

+0

Насколько я понимаю в библиотеках тестов Akka, я думаю, что он запустит систему актеров с диспетчером, который выполняется в вызывающем потоке, поэтому отправка с помощью «actor! Message» фактически блокирует и возвращает завершенное будущее. – johanandren

+0

С другой стороны, я только заметил, что ваш тест не использует тестовые материалы akka (TestBase и т. Д.), А только зонд. Поэтому, чтобы пересмотреть этот ответ, я думаю, что probe.expectMessage будет блокироваться с таймаутом по умолчанию и сбой, если сообщение не поступило. Вы можете указать другое значение таймаута, если хотите. – johanandren