1

我正在 play_2.9.1-2.0.3 上构建一个应用程序使用specs2_2.9.1-1.7.1(与 play 捆绑在一起)进行测试。我有一个看起来像这样的动作:

def createPoll() = Action { request =>
    request.body.asJson.map {jsonBod =>
        Poll.fromJsonValue(jsonBod).fold(
            thrown => CommonResponses.invalidCreatePollRequest(this),
            poll => (CommonResponses.createdPoll(poll, this))
    )}.getOrElse(CommonResponses.expectingJson(this))
}

当我从 curl 向它发送消息时,这可以按预期工作,但是在我的 specs2 测试中,我得到了这个异常:

ClassCastException: java.lang.String cannot be cast to play.api.mvc.AnyContent(PollController.scala:16)

其中第 16 行是:

def createPoll() = Action { request =>

这是测试的相关部分:

    routeAndCall(
        FakeRequest(
            PUT, controllers.routes.PollController.createPoll().url,
            FakeHeaders(),
            "{\"userId\":\"%s\",\"title\":\"%s\"}".format(userId, title)
        ).withHeaders(("Content-type", "application/json"))
    )

如果我将createPolldef 更改为:def createPoll() = Action(parse.tolerantText) {

然后我可以通过 specs2 测试使其工作。

有谁知道我做错了什么?理想情况下,我想使用 parse.json 正文解析器,但我希望能够使用规范而不仅仅是 curl 进行测试。谢谢

4

1 回答 1

1

Action 上的 apply 方法采用Request[AnyContent] => Result. FakeRequest 的参数化类型是第四个参数(请求体)的类型。考虑到这些,问题就很明显了:你试图将 aRequest[String]作为输入传递给一个接受 a 的函数Request[AnyContent]。因此类转换异常。您需要做的就是创建一个带有AnyContentAsJson(A 的子类型AnyContent)的 FakeRequest,如下所示:

import play.api.libs.json.Json.parse

FakeRequest(
        PUT, controllers.routes.PollController.createPoll().url,
        FakeHeaders(),
        AnyContentAsJson(parse("{\"userId\":\"%s\",\"title\":\"%s\"}".format(userId, title)))
    )
于 2012-10-29T01:44:06.043 回答