如何以编程方式执行拒绝处理程序的路由并获得生成的 HttpEntity?
How can I programmatically execute Route of rejection handler and get resulting HttpEntity?
如何以编程方式执行拒绝处理程序的 Route
并获得结果 HttpEntity
?
例如,假设我有 RequestContext
对象和 Rejection
对象,我想对其执行 RejectionHandler.default
并获得 HttpEntity
.
这是我想做的事的例子:
implicit def myRejectionHandler =
RejectionHandler.newBuilder()
.handleAll[Rejection] { rejections ⇒
def prefixEntity(entity: ResponseEntity): ResponseEntity = entity match {
case HttpEntity.Strict(contentType, data) => {
import spray.json._
val text = ErrorResponse(0, "Rejection", data.utf8String).toJson.prettyPrint
HttpEntity(ContentTypes.`application/json`, text)
}
case _ =>
throw new IllegalStateException("Unexpected entity type")
}
val route: Route = extractRequestContext { ctx =>
mapResponseEntity(prefixEntity) {
// Here I want result of `complete` route from RejectionHandler.default
}
}
route
}
.handleNotFound {
complete((NotFound, "Not here!"))
}
.result()
我想我明白了你想要的要点。您可以在您的评论所在的位置应用默认的拒绝处理程序。唯一的问题是 apply
那里 returns 和 Option
如果遇到的拒绝没有命中该拒绝处理程序中的任何内容,那将是 None
。这不太可能,因为您使用的是默认处理程序并且它几乎可以处理所有事情,但您仍然需要在代码中考虑它(因此我的 getOrElse
导致通用 InternalServerError
)。修改后的代码如下所示:
val defaultRejectionHandler = RejectionHandler.default
implicit def myRejectionHandler =
RejectionHandler.newBuilder()
.handleAll[Rejection] { rejections ⇒
def prefixEntity(entity: ResponseEntity): ResponseEntity = entity match {
case HttpEntity.Strict(contentType, data) => {
import spray.json._
val text = ErrorResponse(0, "Rejection", data.utf8String).toJson.prettyPrint
HttpEntity(ContentTypes.`application/json`, text)
}
case _ =>
throw new IllegalStateException("Unexpected entity type")
}
val route: Route = extractRequestContext { ctx =>
mapResponseEntity(prefixEntity) {
defaultRejectionHandler.apply(rejections).getOrElse{
complete(StatusCodes.InternalServerError)
}
}
}
route
}
.handleNotFound {
complete((NotFound, "Not here!"))
}
.result()
这可以编译,但我没有实际测试它是否能达到预期的效果。此外,我不需要 RequestContext
值 ctx
,因此您可以删除其中的 extractRequestContext
层。
如何以编程方式执行拒绝处理程序的 Route
并获得结果 HttpEntity
?
例如,假设我有 RequestContext
对象和 Rejection
对象,我想对其执行 RejectionHandler.default
并获得 HttpEntity
.
这是我想做的事的例子:
implicit def myRejectionHandler =
RejectionHandler.newBuilder()
.handleAll[Rejection] { rejections ⇒
def prefixEntity(entity: ResponseEntity): ResponseEntity = entity match {
case HttpEntity.Strict(contentType, data) => {
import spray.json._
val text = ErrorResponse(0, "Rejection", data.utf8String).toJson.prettyPrint
HttpEntity(ContentTypes.`application/json`, text)
}
case _ =>
throw new IllegalStateException("Unexpected entity type")
}
val route: Route = extractRequestContext { ctx =>
mapResponseEntity(prefixEntity) {
// Here I want result of `complete` route from RejectionHandler.default
}
}
route
}
.handleNotFound {
complete((NotFound, "Not here!"))
}
.result()
我想我明白了你想要的要点。您可以在您的评论所在的位置应用默认的拒绝处理程序。唯一的问题是 apply
那里 returns 和 Option
如果遇到的拒绝没有命中该拒绝处理程序中的任何内容,那将是 None
。这不太可能,因为您使用的是默认处理程序并且它几乎可以处理所有事情,但您仍然需要在代码中考虑它(因此我的 getOrElse
导致通用 InternalServerError
)。修改后的代码如下所示:
val defaultRejectionHandler = RejectionHandler.default
implicit def myRejectionHandler =
RejectionHandler.newBuilder()
.handleAll[Rejection] { rejections ⇒
def prefixEntity(entity: ResponseEntity): ResponseEntity = entity match {
case HttpEntity.Strict(contentType, data) => {
import spray.json._
val text = ErrorResponse(0, "Rejection", data.utf8String).toJson.prettyPrint
HttpEntity(ContentTypes.`application/json`, text)
}
case _ =>
throw new IllegalStateException("Unexpected entity type")
}
val route: Route = extractRequestContext { ctx =>
mapResponseEntity(prefixEntity) {
defaultRejectionHandler.apply(rejections).getOrElse{
complete(StatusCodes.InternalServerError)
}
}
}
route
}
.handleNotFound {
complete((NotFound, "Not here!"))
}
.result()
这可以编译,但我没有实际测试它是否能达到预期的效果。此外,我不需要 RequestContext
值 ctx
,因此您可以删除其中的 extractRequestContext
层。