Middleware compiles
This commit is contained in:
@@ -21,6 +21,7 @@ module PostgREST.Auth (
|
|||||||
import Control.Monad (join)
|
import Control.Monad (join)
|
||||||
import Data.Aeson (Value (..), Object)
|
import Data.Aeson (Value (..), Object)
|
||||||
import Data.Aeson.Types (emptyObject, emptyArray)
|
import Data.Aeson.Types (emptyObject, emptyArray)
|
||||||
|
import qualified Data.ByteString as BS
|
||||||
import Data.Vector as V (null, head)
|
import Data.Vector as V (null, head)
|
||||||
import Data.Map as M (fromList, toList)
|
import Data.Map as M (fromList, toList)
|
||||||
import Data.Monoid ((<>))
|
import Data.Monoid ((<>))
|
||||||
@@ -38,12 +39,12 @@ import qualified Data.HashMap.Lazy as H
|
|||||||
this one is mapped to a SET ROLE statement.
|
this one is mapped to a SET ROLE statement.
|
||||||
In case there is any problem decoding the JWT it returns Nothing.
|
In case there is any problem decoding the JWT it returns Nothing.
|
||||||
-}
|
-}
|
||||||
claimsToSQL :: JWT.ClaimsMap -> [Text]
|
claimsToSQL :: JWT.ClaimsMap -> [BS.ByteString]
|
||||||
claimsToSQL = map setVar . toList
|
claimsToSQL = map setVar . toList
|
||||||
where
|
where
|
||||||
setVar ("role", String val) = setRole val
|
setVar ("role", String val) = setRole val
|
||||||
setVar (k, val) = "set local postgrest.claims." <> pgFmtIdent k <>
|
setVar (k, val) = "set local postgrest.claims." <> cs (pgFmtIdent k) <>
|
||||||
" = " <> valueToVariable val <> ";"
|
" = " <> cs (valueToVariable val) <> ";"
|
||||||
valueToVariable = pgFmtLit . unquoted
|
valueToVariable = pgFmtLit . unquoted
|
||||||
|
|
||||||
{-|
|
{-|
|
||||||
@@ -66,7 +67,7 @@ jwtClaims secret input time =
|
|||||||
customClaims = claim JWT.unregisteredClaims
|
customClaims = claim JWT.unregisteredClaims
|
||||||
|
|
||||||
-- | Receives the name of a role and returns a SET ROLE statement
|
-- | Receives the name of a role and returns a SET ROLE statement
|
||||||
setRole :: Text -> Text
|
setRole :: Text -> BS.ByteString
|
||||||
setRole role = "set local role " <> cs (pgFmtLit role) <> ";"
|
setRole role = "set local role " <> cs (pgFmtLit role) <> ";"
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -24,27 +24,25 @@ import PostgREST.Error (errResponse)
|
|||||||
|
|
||||||
import Prelude hiding(concat)
|
import Prelude hiding(concat)
|
||||||
|
|
||||||
import qualified Data.Vector as V
|
|
||||||
import qualified Data.Map.Lazy as M
|
import qualified Data.Map.Lazy as M
|
||||||
|
|
||||||
runWithClaims :: forall s. AppConfig -> NominalDiffTime ->
|
runWithClaims :: AppConfig -> NominalDiffTime ->
|
||||||
(Request -> H.Session Response) ->
|
(Request -> H.Session Response) ->
|
||||||
Request -> H.Session Response
|
Request -> H.Session Response
|
||||||
runWithClaims conf time app req = do
|
runWithClaims conf time app req = do
|
||||||
_ <- H.unitEx $ stmt setAnon
|
H.sql setAnon
|
||||||
case split (== ' ') (cs auth) of
|
case split (== ' ') (cs auth) of
|
||||||
("Bearer" : tokenStr : _) ->
|
("Bearer" : tokenStr : _) ->
|
||||||
case jwtClaims jwtSecret tokenStr time of
|
case jwtClaims jwtSecret tokenStr time of
|
||||||
Just claims ->
|
Just claims ->
|
||||||
if M.member "role" claims
|
if M.member "role" claims
|
||||||
then do
|
then do
|
||||||
mapM_ H.unitEx $ stmt <$> claimsToSQL claims
|
mapM_ H.sql $ claimsToSQL claims
|
||||||
app req
|
app req
|
||||||
else invalidJWT
|
else invalidJWT
|
||||||
_ -> invalidJWT
|
_ -> invalidJWT
|
||||||
_ -> app req
|
_ -> app req
|
||||||
where
|
where
|
||||||
stmt c = B.Stmt c V.empty True
|
|
||||||
hdrs = requestHeaders req
|
hdrs = requestHeaders req
|
||||||
jwtSecret = configJwtSecret conf
|
jwtSecret = configJwtSecret conf
|
||||||
auth = fromMaybe "" $ lookup hAuthorization hdrs
|
auth = fromMaybe "" $ lookup hAuthorization hdrs
|
||||||
|
|||||||
Reference in New Issue
Block a user