我需要定义一些部分函数来处理具有不同模式的不同url(使用unfinagled):
def indexRoute:PartialFunction[Request, Response] = {
case Path("index") => Ok ~> ResponseString("hello")
}
def notFound:PartialFunction[Request, Response] = {
case Path(_) => NotFound
}
def assetsRoutes:PartialFunction[Request, Response] = {
case Path("assets" :: tail) =>
loadResourceContent(tail) match {
case Some(content) => Ok ~> ResponseString(content)
case _ => NotFound // !!! I don't want to handle it here
}
}
val allRoutes = indexRoute orElse assetsRoutes orElse notFound
你可以看到我最终将一些部分功能组合成一个完整的路线。最后一个是NotFound
处理不匹配的网址,所以我不想关心早期路线中的不匹配情况(例如assertRoutes
)。
但在assetsRoutes
方法中,我无法轻易检查case
部分中是否存在资产,因为我只想触摸一次资产的文件系统。所以我不想写:
def assetsRoutes:PartialFunction[Request, Response] = {
case Path("assets" :: tail) if resoueceExist(tail)=>
val content = loadResourceContent(tail).get
Ok ~> ResponseString(content)
}
虽然我可以写一个自定义unapply
,如:
object AssetExistWithContent {
def unapply(req:Request): Option[String] = {
req match {
case Path("assets" :: tail) => loadResourceContent(tail)
case _ => None
}
}
}
def assetsRoutes:PartialFunction[Request, Response] = {
case AssetExistWithContent(content) => Ok ~> ResponseString(content)
}
但我认为在匹配网址或请求时看到case AssetExistWithContent(content)
部分并不清楚。
所以我想知道是否有可能取消功能体中的当前部分功能?所以我可以写:
def assetsRoutes:PartialFunction[Request, Response] = {
case Path("assets" :: tail) =>
loadResourceContent(tail) match {
case Some(content) => Ok ~> ResponseString(content)
case _ => cancelThisPartialFunction // !!!
}
}
我不需要关心何时使用此方法(NotFound或其他内容),只需告诉来电者我无法处理,请尝试下一个。
答案 0 :(得分:3)
如您所述,无法取消PartialFunction
。但是,您可以定义一个更简单的提取器:
object LoadableContent {
def unapply(req: List[String]): Option[String] = loadResourceContent(req)
}
并使用它:
def assetsRoutes: PartialFunction[Request, Response] = {
case Path("assets" :: LoadableContent(content)) =>
Ok ~> ResponseString(content)
}