Skip to content

Instantly share code, notes, and snippets.

@saurabhnanda
Created June 27, 2019 08:34
Show Gist options
  • Save saurabhnanda/20df208f9dd89c1f21f931e42952d79a to your computer and use it in GitHub Desktop.
Save saurabhnanda/20df208f9dd89c1f21f931e42952d79a to your computer and use it in GitHub Desktop.
data Permission = PermA | PermB | PermC deriving (Eq, Show)
data EnsurePermissions (ps :: [Permission]) = EnsurePermissions
instance ( HasServer api context
) => HasServer (EnsurePermissions (ps :: [Permission]) :> api) context where
type ServerT (EnsurePermissions ps :> api) m = (() -> ServerT api m)
-- I want to convert the type `ps` to it's equivalent value in this function
route Proxy context subserver = undefined
@Solonarv
Copy link

{-# LANGUAGE DataKinds, FlexibleInstances, ScopedTypeVariables, TypeApplications #-}

class KnownPermissions (ps :: [Permission]) where
  perms :: Proxy ps -> [Permission]

instance KnownPermissions '[] where
  perms _ = []

instance KnownPermissions ps => KnownPermissions ('PermA ': ps) where
  perms _ = PermA : perms (Proxy @ps)

-- same boilerplate for PermB, PermC

@Solonarv
Copy link

Solonarv commented Jun 27, 2019

Using singletons:

{-# LANGUAGE
    DataKinds,
    FlexibleInstances,
    ScopedTypeVariables,
    TypeApplications
    #-}
import Data.Singletons

data Permission = PermA | PermB | PermC

$(genSingletons ''Permission)

instance ( HasServer api context
         , SingI ps
         ) => HasServer (EnsurePermissions (ps :: [Permission]) :> api) context  where
  type ServerT (EnsurePermissions ps :> api) m = (() -> ServerT api m)
  route _ context subserver = ... fromSing (sing @ps) ...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment