Play应用中的POST内部重定向?

时间:2013-05-14 18:11:37

标签: java scala model-view-controller playframework-2.0

我正在使用Play Framework 2.0.3,并希望添加一个过滤器,内部重新路由某些请求(即没有 301/302 )到应用中确定动态的网址。也就是说,我需要转发的端点取决于请求,因此我不知道在编译时它将是哪个控制器/操作,并且不能直接调用它们。

例如,如果我收到GET /foo?redirectTo=/bar的请求,我怎么能让Play内部路由/处理它,好像它实际上是POST /bar

这个要点到目前为止是我最好的猜测,但它有一些限制:https://gist.github.com/brikis98/5582159

3 个答案:

答案 0 :(得分:0)

只需调用相应的控制器方法。

Java版:

public static Result foo() {
    return bar();
}

public static Result bar() {
    return ok();
}

我错过了什么吗?

答案 1 :(得分:0)

因此,您需要将请求从GET请求转换为POST。 我不知道有任何自动方式,但它应该相当容易。

你能解释一下为什么需要它吗?

于连。

答案 2 :(得分:0)

好的,这是一个似乎有效的解决方案:

object RedirectFilter extends Filter {

  def apply(next: RequestHeader => Result)(request: RequestHeader): Result = {

    getRedirectParams(request).flatMap { case (newRequest, body) =>
      route(newRequest).map { iteratee =>
        AsyncResult(Enumerator(body).run(iteratee))
      }
    } getOrElse {
      next(request)
    }
  }

  private def getRedirectParams(request: RequestHeader): Option[(RequestHeader, Array[Byte])] = {
    if (someCondition) {
      Some(toPostRequest(request), "Some new body data".getBytes("UTF-8"))      
    } else {
      None
    }
  }

  private def toPostRequest(originalRequest: RequestHeader): RequestHeader = {
    originalRequest.copy(
      uri = "/some/new/uri",
      path = "/some/new/uri",
      method = "POST"
    )
  }

  private def route(request: RequestHeader): Option[Iteratee[Array[Byte], Result]] = {
    Play.global.onRouteRequest(request).collect {
      case action: EssentialAction => Play.global.doFilter(action)(request)
    }
  }

}

查看this gist以获取其他一些有用的评论。