1

对于上下文,这是一种身份验证情况。在我的应用程序中,如果客户端没有经过身份验证,那么应用程序显然需要做出适当的响应。当我想根据调用服务器的应用程序类型选择不同的响应时,挑战就出现了。

下面是一个路由示例:

server =    Header "Cookie" (AuthToken Unverified)
         :> "api" :> "history" :> Get '[HTML, JSON] HistoryPage

因此,HTML 响应将针对 CGI 应用程序。通常,它应该呈现一个身份验证页面,或者它应该抛出一个 303 以将用户引导到一个身份验证页面。

但是 JSON 响应将用于 Javascript 应用程序,我想简单地返回 404,因为 Javascript 将有其他方式进行身份验证。

这是我的顶级处理程序:

newtype WebM a = WebM (ReaderT Context (ExceptT WebExc IO) a)
data WebExc = OtherExceptionTypes
            | AppUnauthorized

runWeb :: Context -> WebM :~> Handler
runWeb ctx@Context{..} = Nat $ \(WebM action) -> withExceptT trExc $ runReaderT action ctx
  where
    trExc :: WebExc -> ServantErr
    trExc AppUnauthorized = err303 { .. }

我尝试创建自己的 Javascript 内容类型,但 MimeRenderer 不允许我抛出异常。到目前为止,我唯一的想法是捕获“接受”标头并在处理程序内303404从处理程序中抛出。但这很糟糕,因为处理程序不应该知道有关实际客户端应用程序的任何信息。

有没有更清洁的方法来处理这个?

4

1 回答 1

1

不完全回答你的问题,但从更大的角度来看,这听起来像是两条独立路线的用例,它们之间共享一个共同的实现位。

于 2017-03-09T18:03:41.523 回答