unitym-servant-0.1.0.0: src/Network/UnityM/Servant.hs
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{- |
Module : Network.UnityM.Servant
Description : The Unity Monad implementation for Servant
Copyright : (c) Brian Hurt, 2017
License : BSD3
Maintainer : bhurt42@gmail.com
Stability : experimental
Portability : Haskell
This is the implementation of the Unity monad for Servant. I assume that
the code is using enter to add a ReaderT or StateT on top of the Handler
monad.
Note that if we try to supply a implementation of UnityM for MTL's Reader
type class, this conflicts with the Trans implementation of UnityM in the
main library. This whole implementation is tap dancing on the edge of
needing OverlappingInstances, which is bad. For more complex instances,
hand rolled implementations of UnityM may be required.
-}
module Network.UnityM.Servant where
import Control.Monad.Except
import Network.UnityM
import qualified Control.Monad.Trans.Reader as TransR
import qualified Control.Monad.Trans.State as TransS
import qualified Data.Text as Text
import Servant
instance {-# OVERLAPPING #-}
UnityM c (TransR.ReaderT c Handler) where
getContext = TransR.ask
permissionDenied msg = lift $ throwError (err403
{ errReasonPhrase =
Text.unpack msg })
instance {-# OVERLAPPING #-}
UnityM c (TransS.StateT c Handler) where
getContext = TransS.get
permissionDenied msg = lift $ throwError (err403
{ errReasonPhrase =
Text.unpack msg })