18

我知道在 Play 2.0 (scala) 中设置 HTTP 标头?您可以根据具体情况设置响应标头,例如,Ok("hello").withHeaders(PRAGMA -> "no-cache").

如果您想在所有操作的响应中设置该标头或几个不同的标头怎么办?你不想withHeaders到处重复。而且由于这更像是应用程序范围的配置,您可能不希望 Action 编写者必须使用不同的语法来获取您的标头(例如OkWithHeaders(...)

我现在拥有的是一个看起来像的基本 Controller 类

class ContextController extends Controller {
 ...
 def Ok(h: Html) = Results.Ok(h).withHeaders(PRAGMA -> "no-cache")
}

但这感觉不太对。感觉应该有更多 AOP 风格的方式来定义默认标头并将它们添加到每个响应中。

4

4 回答 4

14

这个话题现在已经很老了,但是在 Play 2.1 中它现在变得更加简单了。你的Global.scala班级应该是这样的:

import play.api._
import play.api.mvc._
import play.api.http.HeaderNames._

/**
 * Global application settings.
 */
object Global extends GlobalSettings {

  /**
   * Global action composition.
   */
  override def doFilter(action: EssentialAction): EssentialAction = EssentialAction { request =>
    action.apply(request).map(_.withHeaders(
      PRAGMA -> "no-cache"
    ))
  }
}
于 2013-02-15T13:54:38.540 回答
8

在您的Global.scala中,将每个调用包装在一个操作中:

import play.api._
import play.api.mvc._
import play.api.Play.current
import play.api.http.HeaderNames._

object Global extends GlobalSettings {

  def NoCache[A](action: Action[A]): Action[A] = Action(action.parser) { request =>
    action(request) match {
      case s: SimpleResult[_] => s.withHeaders(PRAGMA -> "no-cache")
      case result => result
    }
  }

  override def onRouteRequest(request: RequestHeader): Option[Handler] = {
    if (Play.isDev) {
      super.onRouteRequest(request).map {
        case action: Action[_] => NoCache(action)
        case other => other
      }
    } else {
      super.onRouteRequest(request)
    }
  }

}

在这种情况下,我只在开发模式下调用该操作,这对于无缓存指令最有意义。

于 2012-07-30T07:02:11.453 回答
3

实现细粒度控制的最简单方法是使用包装的操作。在你的情况下,它可能是这样的:

object HeaderWriter {
    def apply(f: Request[AnyContent] => SimpleResult):Action[AnyContent] = {
        Action { request =>
            f(request).withHeaders(PRAGMA -> "no-cache")
        }
    }
}

并以这种方式使用它:

def doAction = HeaderWriter { request =>
    ... do any stuff your want ...
    Ok("Thats it!")
}
于 2012-12-15T09:38:36.297 回答
0

方法也很多。您可以使用action-composition。然后,您必须在要在此处设置的每个控制器上声明标头。另一种选择是使用GlobalSettings。java也有类似的解决方案。

于 2012-07-14T06:17:51.980 回答