From 13fcb4f3f104e0941182da5b83e43b0bf9efcb09 Mon Sep 17 00:00:00 2001 From: Christian Marie Date: Thu, 14 May 2015 00:07:57 +1000 Subject: [PATCH 1/2] servant: clean up some white spaces, add link explaining why Or works. --- servant/src/Servant/Utils/Links.hs | 47 ++++++++++++++++-------------- 1 file changed, 25 insertions(+), 22 deletions(-) diff --git a/servant/src/Servant/Utils/Links.hs b/servant/src/Servant/Utils/Links.hs index 2a5cebf0..853cf995 100644 --- a/servant/src/Servant/Utils/Links.hs +++ b/servant/src/Servant/Utils/Links.hs @@ -137,16 +137,19 @@ data Link = Link } deriving Show -- | If either a or b produce an empty constraint, produce an empty constraint. +-- +-- This works because of: +-- https://ghc.haskell.org/trac/ghc/wiki/NewAxioms/CoincidentOverlap type family Or (a :: Constraint) (b :: Constraint) :: Constraint where Or () b = () Or a () = () -- | If both a or b produce an empty constraint, produce an empty constraint. type family And (a :: Constraint) (b :: Constraint) :: Constraint where - And () () = () + And () () = () --- | You may use this type family to tell the type checker that your custom type --- may be skipped as part of a link. This is useful for things like +-- | You may use this type family to tell the type checker that your custom +-- type may be skipped as part of a link. This is useful for things like -- 'QueryParam' that are optional in a URI and do not affect them if they are -- omitted. -- @@ -162,30 +165,30 @@ type family IsElem' a s :: Constraint -- | Closed type family, check if endpoint is within api type family IsElem endpoint api :: Constraint where - IsElem e (sa :<|> sb) = Or (IsElem e sa) (IsElem e sb) - IsElem (e :> sa) (e :> sb) = IsElem sa sb - IsElem sa (Header x :> sb) = IsElem sa sb - IsElem sa (ReqBody y x :> sb) = IsElem sa sb - IsElem (e :> sa) (Capture x y :> sb) = IsElem sa sb - IsElem sa (QueryParam x y :> sb) = IsElem sa sb - IsElem sa (QueryParams x y :> sb) = IsElem sa sb - IsElem sa (QueryFlag x :> sb) = IsElem sa sb - IsElem sa (MatrixParam x y :> sb) = IsElem sa sb - IsElem sa (MatrixParams x y :> sb) = IsElem sa sb - IsElem sa (MatrixFlag x :> sb) = IsElem sa sb - IsElem (Get ct typ) (Get ct' typ) = IsSubList ct ct' - IsElem (Post ct typ) (Post ct' typ) = IsSubList ct ct' - IsElem (Put ct typ) (Put ct' typ) = IsSubList ct ct' - IsElem (Delete ct typ) (Delete ct' typ) = IsSubList ct ct' - IsElem e e = () - IsElem e a = IsElem' e a + IsElem e (sa :<|> sb) = Or (IsElem e sa) (IsElem e sb) + IsElem (e :> sa) (e :> sb) = IsElem sa sb + IsElem sa (Header x :> sb) = IsElem sa sb + IsElem sa (ReqBody y x :> sb) = IsElem sa sb + IsElem (e :> sa) (Capture x y :> sb) = IsElem sa sb + IsElem sa (QueryParam x y :> sb) = IsElem sa sb + IsElem sa (QueryParams x y :> sb) = IsElem sa sb + IsElem sa (QueryFlag x :> sb) = IsElem sa sb + IsElem sa (MatrixParam x y :> sb) = IsElem sa sb + IsElem sa (MatrixParams x y :> sb) = IsElem sa sb + IsElem sa (MatrixFlag x :> sb) = IsElem sa sb + IsElem (Get ct typ) (Get ct' typ) = IsSubList ct ct' + IsElem (Post ct typ) (Post ct' typ) = IsSubList ct ct' + IsElem (Put ct typ) (Put ct' typ) = IsSubList ct ct' + IsElem (Delete ct typ) (Delete ct' typ) = IsSubList ct ct' + IsElem e e = () + IsElem e a = IsElem' e a type family IsSubList a b :: Constraint where - IsSubList '[] b = () + IsSubList '[] b = () IsSubList '[x] (x ': xs) = () IsSubList '[x] (y ': ys) = IsSubList '[x] ys - IsSubList (x ': xs) y = IsSubList '[x] y `And` IsSubList xs y + IsSubList (x ': xs) y = IsSubList '[x] y `And` IsSubList xs y -- Phantom types for Param data Matrix From d1b904372da06b2f0135e5927aa3ccf7b14bff82 Mon Sep 17 00:00:00 2001 From: Christian Marie Date: Fri, 15 May 2015 10:37:18 +1000 Subject: [PATCH 2/2] Move comment out of haddocks. --- servant/src/Servant/Utils/Links.hs | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/servant/src/Servant/Utils/Links.hs b/servant/src/Servant/Utils/Links.hs index 853cf995..8b9537af 100644 --- a/servant/src/Servant/Utils/Links.hs +++ b/servant/src/Servant/Utils/Links.hs @@ -137,10 +137,9 @@ data Link = Link } deriving Show -- | If either a or b produce an empty constraint, produce an empty constraint. --- --- This works because of: --- https://ghc.haskell.org/trac/ghc/wiki/NewAxioms/CoincidentOverlap type family Or (a :: Constraint) (b :: Constraint) :: Constraint where + -- This works because of: + -- https://ghc.haskell.org/trac/ghc/wiki/NewAxioms/CoincidentOverlap Or () b = () Or a () = ()