如何在Play Framework 2.3.x中用Scala代码启用HSTS并本地测试?
嘿,针对你用Play 2.3.6版本添加HSTS响应头的需求,我给你整理了适配旧版本的方案——毕竟2.3.x确实没法用高版本的重定向过滤器,咱们得用适合这个版本的办法👇
一、给Play 2.3.x添加HSTS响应头的核心方案
Play 2.3.x没有内置的HSTS过滤器,所以咱们得自己实现全局或局部的响应拦截,手动添加头信息。
方法1:全局过滤器(推荐,所有请求自动生效)
通过继承GlobalSettings拦截所有请求,在返回响应时统一追加HSTS头,不用逐个修改Controller的Action。
代码示例:
import play.api.mvc._ import play.api.GlobalSettings object Global extends GlobalSettings { override def onHandlerRequest(request: RequestHeader, handler: Handler): Handler = { handler match { // 拦截所有Action类型的请求处理 case action: Action[_] => Action(action.parser) { req => action(req).map(result => result.withHeaders( // 配置HSTS规则:缓存1年,包含子域名(按需调整) "Strict-Transport-Security" -> "max-age=31536000; includeSubDomains" // 如果要开启预加载(生产环境需提交到HSTS列表),可以加"; preload" ) ) case other => other } } }
方法2:局部Action包装器(仅特定接口生效)
如果不想全局添加,只想给部分Action加HSTS头,可以写一个包装函数:
import play.api.mvc._ object HstsAction { def apply[A](action: Action[A]): Action[A] = Action(action.parser) { req => action(req).map(_.withHeaders( "Strict-Transport-Security" -> "max-age=31536000" )) } }
然后在Controller里直接用:
def index = HstsAction { Ok("Hello with HSTS") }
二、本地测试的最优方案
你现在用http://localhost:9000测试,这里要注意:HSTS头仅在HTTPS请求下会被浏览器识别生效,HTTP请求里浏览器会直接忽略它。不过有两种方式可以验证:
方案1:本地启用HTTPS(最贴近生产场景)
给Play 2.3.x配置HTTPS端点,用https://localhost:9000访问,就能模拟真实环境下的HSTS行为。
- 在
conf/application.conf里添加HTTPS配置:
play.server.https.port=9000 play.server.https.keyStore.path="conf/localhost.jks" play.server.https.keyStore.password="your-password"
- 生成本地自签名证书(用keytool命令):
keytool -genkey -alias localhost -keyalg RSA -keystore conf/localhost.jks -keysize 2048
执行命令后按提示输入信息,密码要和配置里的一致。启动应用后,用https://localhost:9000访问(浏览器会提示证书不安全,忽略即可),用Postman就能看到响应头里的HSTS字段了。
方案2:HTTP下直接验证头存在(快速测试代码)
如果不想配置HTTPS,也可以直接用HTTP请求——虽然浏览器会忽略这个头,但Postman能直接看到响应头是否存在。上面的全局/局部方案都会给HTTP响应也加上HSTS头,所以用Postman请求http://localhost:9000,查看响应头就能确认代码是否生效。
三、小总结
- 全局过滤器是最优方案,避免遗漏任何路由;
- 本地测试优先选HTTPS方式,更贴合生产环境;
- 生产环境中建议根据业务需求调整
max-age,需要覆盖子域名就加includeSubDomains,要加入HSTS预加载列表再添加preload。
内容的提问来源于stack exchange,提问作者jerald
相关产品推荐
相关产品推荐

