Scala Play 框架 rest api 从请求到响应添加令牌

Scala Play framework rest api add token from request to response

我正试图让我所有的休息 api 端点 return 用户用来发出请求的令牌(已经存在于所有请求中)。 这就是我的基本端点的样子:

def getAll(meta: MetaData): Action[AnyContent] = deadbolt.Restrict(role)(parse.default) { 
    implicit request => myService.getAll(meta).map(result => {
        val results: Seq[Resp] = result._2.map(res => Mapper(res))
        Ok(Json.toJson(MyListResponse.apply(meta, result._1, results)))
    })
}

如何将请求中收到的令牌信息添加到我的响应中? 谢谢!

正如您在评论部分所述,您需要从查询参数中获取令牌并将其添加到响应 header。假设此标记是可选的,因此可能不存在,因此可以通过以下方式实现:

implicit request => myService.getAll(meta).map { result => 
   // Fetch optional token as query parameter. `token_parameter` - parameter key
   val requestToken = request.queryString.get("token_parameter").flatMap(_.headOption)
   val results: Seq[Resp] = result._2.map(res => Mapper(res))
   val body = Json.toJson(MyListResponse.apply(meta, result._1, results))

   // Add token to header if it is present
   requestToken.fold(Ok(body))(token => Ok(body).withHeaders("token_header" -> token))
}

更新

为了将此逻辑应用于所有路线,您可以使用播放过滤器功能。请参阅文档以获取更多详细信息:https://www.playframework.com/documentation/latest/ScalaHttpFilters

您需要做的事情:

1) 实现您自己的 Play Filter。它看起来像下一个:

import javax.inject.Inject
import akka.stream.Materializer
import play.api.mvc._
import scala.concurrent.ExecutionContext
import scala.concurrent.Future

class TokenFilter @Inject() (implicit val mat: Materializer, ec: ExecutionContext) extends Filter {
      def apply(nextFilter: RequestHeader => Future[Result])
               (requestHeader: RequestHeader): Future[Result] = {
            nextFilter(requestHeader).map { result =>
                val requestToken = requestHeader.queryString.get("token_parameter").flatMap(_.headOption)
                requestToken.fold(result )(token => result.withHeaders("token_header" -> token))
            }
    }
}

2) 将过滤器连接到应用程序的其余部分。例如,通过在 application.conf

中添加下一个配置
play.http.filters += com.yourcomany.TokenFilter

希望对您有所帮助!