{-# LANGUAGE MultiParamTypeClasses #-} {-# LANGUAGE FlexibleInstances #-} {-# LANGUAGE KindSignatures #-} {-# LANGUAGE TypeOperators #-} {-# LANGUAGE Rank2Types #-} {-# LANGUAGE DataKinds #-} {-# LANGUAGE GADTs #-} {-# LANGUAGE CPP #-} #if __GLASGOW_HASKELL__ < 710 {-# LANGUAGE OverlappingInstances #-} #endif module Data.Apiary.Extension.Internal ( Initializer(..) , Has(..) , allMiddleware' , allMiddleware ) where #if __GLASGOW_HASKELL__ >= 708 import qualified Control.Category as Cat #endif import qualified Network.Wai as Wai import Control.Monad.Apiary.Action.Internal ( Extensions(AddExtension, NoExtension) , Extension(extMiddleware, extMiddleware'), Middleware') class Has a (as :: [*]) where getExtension :: proxy a -> Extensions as -> a instance Has a (a ': as) where getExtension _ (AddExtension a _) = a #if __GLASGOW_HASKELL__ >= 710 instance {-# OVERLAPPABLE #-} Has a as => Has a (a' ': as) where #else instance Has a as => Has a (a' ': as) where #endif getExtension p (AddExtension _ as) = getExtension p as newtype Initializer m i o = Initializer {unInitializer :: forall a. Extensions i -> (Extensions o -> m a) -> m a} allMiddleware' :: Extensions es -> Middleware' allMiddleware' NoExtension = id allMiddleware' (AddExtension e es) = extMiddleware' e . allMiddleware' es allMiddleware :: Extensions es -> Wai.Middleware allMiddleware NoExtension = id allMiddleware (AddExtension e es) = extMiddleware e . allMiddleware es #if __GLASGOW_HASKELL__ >= 708 instance Monad m => Cat.Category (Initializer m) where id = Initializer $ \es m -> m es Initializer a . Initializer b = Initializer $ \e m -> b e (\e' -> a e' m) #endif