Play 2.3 override global SecurityHeadersFilter X-FRAME-OPTIONS 用于特定操作
Play 2.3 override global SecurityHeadersFilter X-FRAME-OPTIONS for a specific action
我在 Play 2.3 中全局启用了 SecurityHeadersFilter。
这是我的设置:
play.filters.headers.frameOptions="SAMEORIGIN"
但是我怎样才能用 X-Frame-Options=GOFORIT 而不是 SAMEORIGIN 覆盖一个动作?
使用动作组合。
首先,创建动作:
import play.libs.F.Promise;
import play.mvc.Action.Simple;
import play.mvc.Http.Context;
import play.mvc.Result;
public class XFrameOptionAction extends Simple {
@Override
public Promise<Result> call(Context ctx) throws Throwable {
ctx.response().setHeader("X-Frame-Options", "GOFORIT");
return delegate.call(ctx);
}
}
然后,在你的控制器中使用它
import play.mvc.Controller;
import play.mvc.Result;
import play.mvc.With;
public class MyController extends Controller {
@With(XFrameOptionAction.class)
public static Result index() {
return ok();
}
}
这将为 MyController
的 index
操作添加 header。
您还可以将注释放在控制器级别,以使控制器的所有操作都像这样。
如果你想让它对你的所有控制器通用,你需要创建一个你的所有控制器都将扩展的控制器。
这就是我用来避免 header 不被 SecurityHeadersFilter 覆盖的方法。
import play.api.libs.iteratee._
object FilterChainByRequestHeader {
def apply[A](action: EssentialAction, filtersFun: (RequestHeader) => List[EssentialFilter]): EssentialAction = new EssentialAction {
def apply(rh: RequestHeader): Iteratee[Array[Byte], Result] = {
val chain = filtersFun(rh).reverse.foldLeft(action) { (a, i) => i(a) }
chain(rh)
}
}
}
val securityFilter = SecurityHeadersFilter()
val defaultFilters = List(securityFilter)
def filters(rh: RequestHeader) = {
if (rh.path.startsWith("/cors_path"))
defaultFilters.filterNot(_.eq(securityFilter))
else defaultFilters
}
override def doFilter(a: EssentialAction): EssentialAction = {
FilterChainByRequestHeader(super.doFilter(a), filters)
}
我在 Play 2.3 中全局启用了 SecurityHeadersFilter。
这是我的设置:
play.filters.headers.frameOptions="SAMEORIGIN"
但是我怎样才能用 X-Frame-Options=GOFORIT 而不是 SAMEORIGIN 覆盖一个动作?
使用动作组合。
首先,创建动作:
import play.libs.F.Promise;
import play.mvc.Action.Simple;
import play.mvc.Http.Context;
import play.mvc.Result;
public class XFrameOptionAction extends Simple {
@Override
public Promise<Result> call(Context ctx) throws Throwable {
ctx.response().setHeader("X-Frame-Options", "GOFORIT");
return delegate.call(ctx);
}
}
然后,在你的控制器中使用它
import play.mvc.Controller;
import play.mvc.Result;
import play.mvc.With;
public class MyController extends Controller {
@With(XFrameOptionAction.class)
public static Result index() {
return ok();
}
}
这将为 MyController
的 index
操作添加 header。
您还可以将注释放在控制器级别,以使控制器的所有操作都像这样。
如果你想让它对你的所有控制器通用,你需要创建一个你的所有控制器都将扩展的控制器。
这就是我用来避免 header 不被 SecurityHeadersFilter 覆盖的方法。
import play.api.libs.iteratee._
object FilterChainByRequestHeader {
def apply[A](action: EssentialAction, filtersFun: (RequestHeader) => List[EssentialFilter]): EssentialAction = new EssentialAction {
def apply(rh: RequestHeader): Iteratee[Array[Byte], Result] = {
val chain = filtersFun(rh).reverse.foldLeft(action) { (a, i) => i(a) }
chain(rh)
}
}
}
val securityFilter = SecurityHeadersFilter()
val defaultFilters = List(securityFilter)
def filters(rh: RequestHeader) = {
if (rh.path.startsWith("/cors_path"))
defaultFilters.filterNot(_.eq(securityFilter))
else defaultFilters
}
override def doFilter(a: EssentialAction): EssentialAction = {
FilterChainByRequestHeader(super.doFilter(a), filters)
}