graphql-engine-1.0.0: GraphQL API over Postgres
Safe HaskellNone
LanguageHaskell2010

Hasura.RQL.DDL.Webhook.Transform

Description

Webhook Transformations are data transformations used to modify HTTP Requests/Responses before requests are executed and after responses are received.

Transformations are supplied by users as part of the Metadata for a particular Action or EventTrigger as a RequestTransform record. Per-field Transformations are stored as data (defunctionalized), often in the form of a Kriti template, and then converted into actual functions (reified) at runtime by the Transform typeclass.

We take a Higher Kinded Data (HKD) approach to representing the transformations. RequestFields is an HKD which can represent the actual request data as 'RequestFields Identity' or the defunctionalized transforms as 'RequestFields (WithOptional TransformFn)'.

We can then traverse over the entire RequestFields HKD to reify all the fields at once and apply them to our actual request data.

NOTE: We don't literally use traverse or the HKD equivalent btraverse, but you can think of this operation morally as a traversal. See applyRequestTransform for implementation details.

Synopsis

Documentation

data RequestTransform Source #

RequestTransform is the metadata representation of a request transformation. It consists of a record of higher kinded data (HKD) along with some regular data. We seperate the HKD data into its own record field called requestFields which we nest inside our non-HKD record. The actual transformation operations are contained in the HKD.

Instances

Instances details
Eq RequestTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Show RequestTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Generic RequestTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Associated Types

type Rep RequestTransform :: Type -> Type #

NFData RequestTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

rnf :: RequestTransform -> () #

FromJSON RequestTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

parseJSON :: Value -> Parser RequestTransform

parseJSONList :: Value -> Parser [RequestTransform]

ToJSON RequestTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Cacheable RequestTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

type Rep RequestTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

type Rep RequestTransform = D1 ('MetaData "RequestTransform" "Hasura.RQL.DDL.Webhook.Transform" "graphql-engine-1.0.0-inplace" 'False) (C1 ('MetaCons "RequestTransform" 'PrefixI 'True) (S1 ('MetaSel ('Just "version") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedStrict) (Rec0 Version) :*: (S1 ('MetaSel ('Just "requestFields") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedStrict) (Rec0 (RequestFields (WithOptional TransformFn))) :*: S1 ('MetaSel ('Just "templateEngine") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedStrict) (Rec0 TemplatingEngine))))

type RequestTransformFns = RequestFields (WithOptional TransformFn) Source #

Defunctionalized Webhook Transformation

We represent a defunctionalized request transformation by parameterizing our HKD with WithOptional TransformFn, which marks each of the fields as optional and supplies the appropriate transformation function to them if if they are provided.

type RequestData = RequestFields Identity Source #

Actual Request Data

We represent the actual request data by parameterizing our HKD with Identity, which allows us to trivially unwrap the fields (which should exist after any transformations have been applied).

data RequestFields f Source #

This is our HKD type. It is a record with fields for each component of an Request we wish to transform.

Constructors

RequestFields 

Fields

Instances

Instances details
FromJSON RequestTransformFns Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

parseJSON :: Value -> Parser RequestTransformFns

parseJSONList :: Value -> Parser [RequestTransformFns]

ToJSON RequestTransformFns Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

AllBF Eq f RequestFields => Eq (RequestFields f) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

AllBF Show f RequestFields => Show (RequestFields f) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Generic (RequestFields f) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Associated Types

type Rep (RequestFields f) :: Type -> Type #

AllBF NFData f RequestFields => NFData (RequestFields f) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

rnf :: RequestFields f -> () #

AllBF Cacheable f RequestFields => Cacheable (RequestFields f) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

ApplicativeB RequestFields Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

bpure :: (forall (a :: k). f a) -> RequestFields f

bprod :: forall (f :: k -> Type) (g :: k -> Type). RequestFields f -> RequestFields g -> RequestFields (Product f g)

ConstraintsB RequestFields Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Associated Types

type AllB c RequestFields

Methods

baddDicts :: forall (c :: k -> Constraint) (f :: k -> Type). AllB c RequestFields => RequestFields f -> RequestFields (Product (Dict c) f)

FunctorB RequestFields Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

bmap :: (forall (a :: k). f a -> g a) -> RequestFields f -> RequestFields g

TraversableB RequestFields Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

btraverse :: Applicative e => (forall (a :: k). f a -> e (g a)) -> RequestFields f -> e (RequestFields g)

type Rep (RequestFields f) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

type Rep (RequestFields f) = D1 ('MetaData "RequestFields" "Hasura.RQL.DDL.Webhook.Transform" "graphql-engine-1.0.0-inplace" 'False) (C1 ('MetaCons "RequestFields" 'PrefixI 'True) ((S1 ('MetaSel ('Just "method") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedStrict) (Rec0 (f Method)) :*: S1 ('MetaSel ('Just "url") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedStrict) (Rec0 (f Url))) :*: (S1 ('MetaSel ('Just "body") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedStrict) (Rec0 (f Body)) :*: (S1 ('MetaSel ('Just "queryParams") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedStrict) (Rec0 (f QueryParams)) :*: S1 ('MetaSel ('Just "requestHeaders") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedStrict) (Rec0 (f Headers))))))
type AllB (c :: Type -> Constraint) RequestFields Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

type AllB (c :: Type -> Constraint) RequestFields = GAll 0 c (GAllRepB RequestFields)

requestL :: Lens' Request RequestData Source #

A 'Lens'' for viewing a Request as our RequestData HKD; it does so by wrapping each of the matching request fields in a corresponding TransformFn.

XXX: This function makes internal usage of decodeUtf8, which throws an impure exception when the supplied ByteString cannot be decoded into valid UTF8 text!

applyRequestTransform :: forall m. MonadError TransformErrorBundle m => (Request -> RequestTransformCtx) -> RequestTransformFns -> Request -> m Request Source #

Transform an Request with a RequestTransform.

Note: we pass in the request url explicitly for use in the ReqTransformCtx. We do this so that we can ensure that the url is syntactically identical to what the use submits. If we use the parsed request from the Request term then it is possible that the url is semantically equivalent but syntactically different. An example of this is the presence or lack of a trailing slash on the URL path. This important when performing string interpolation on the request url.

newtype WithOptional f result Source #

Enrich a Functor f with optionality; this is primarily useful when one wants to annotate fields as optional when using the Higher-Kinded Data pattern.

WithOptional f is equivalent to Compose Maybe f.

Constructors

WithOptional 

Fields

Instances

Instances details
FromJSON RequestTransformFns Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

parseJSON :: Value -> Parser RequestTransformFns

parseJSONList :: Value -> Parser [RequestTransformFns]

ToJSON RequestTransformFns Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Functor f => Functor (WithOptional f) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

fmap :: (a -> b) -> WithOptional f a -> WithOptional f b #

(<$) :: a -> WithOptional f b -> WithOptional f a #

Foldable f => Foldable (WithOptional f) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

fold :: Monoid m => WithOptional f m -> m #

foldMap :: Monoid m => (a -> m) -> WithOptional f a -> m #

foldMap' :: Monoid m => (a -> m) -> WithOptional f a -> m #

foldr :: (a -> b -> b) -> b -> WithOptional f a -> b #

foldr' :: (a -> b -> b) -> b -> WithOptional f a -> b #

foldl :: (b -> a -> b) -> b -> WithOptional f a -> b #

foldl' :: (b -> a -> b) -> b -> WithOptional f a -> b #

foldr1 :: (a -> a -> a) -> WithOptional f a -> a #

foldl1 :: (a -> a -> a) -> WithOptional f a -> a #

toList :: WithOptional f a -> [a] #

null :: WithOptional f a -> Bool #

length :: WithOptional f a -> Int #

elem :: Eq a => a -> WithOptional f a -> Bool #

maximum :: Ord a => WithOptional f a -> a #

minimum :: Ord a => WithOptional f a -> a #

sum :: Num a => WithOptional f a -> a #

product :: Num a => WithOptional f a -> a #

Eq (f result) => Eq (WithOptional f result) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

(==) :: WithOptional f result -> WithOptional f result -> Bool #

(/=) :: WithOptional f result -> WithOptional f result -> Bool #

Show (f result) => Show (WithOptional f result) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

showsPrec :: Int -> WithOptional f result -> ShowS #

show :: WithOptional f result -> String #

showList :: [WithOptional f result] -> ShowS #

Generic (WithOptional f result) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Associated Types

type Rep (WithOptional f result) :: Type -> Type #

Methods

from :: WithOptional f result -> Rep (WithOptional f result) x #

to :: Rep (WithOptional f result) x -> WithOptional f result #

NFData (f result) => NFData (WithOptional f result) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

rnf :: WithOptional f result -> () #

FromJSON (f result) => FromJSON (WithOptional f result) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

parseJSON :: Value -> Parser (WithOptional f result)

parseJSONList :: Value -> Parser [WithOptional f result]

ToJSON (f result) => ToJSON (WithOptional f result) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

toJSON :: WithOptional f result -> Value

toEncoding :: WithOptional f result -> Encoding

toJSONList :: [WithOptional f result] -> Value

toEncodingList :: [WithOptional f result] -> Encoding

Cacheable (f result) => Cacheable (WithOptional f result) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

unchanged :: Accesses -> WithOptional f result -> WithOptional f result -> Bool Source #

type Rep (WithOptional f result) Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

type Rep (WithOptional f result) = D1 ('MetaData "WithOptional" "Hasura.RQL.DDL.Webhook.Transform" "graphql-engine-1.0.0-inplace" 'True) (C1 ('MetaCons "WithOptional" 'PrefixI 'True) (S1 ('MetaSel ('Just "getOptional") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedLazy) (Rec0 (Maybe (f result)))))

withOptional :: forall a b f. Coercible a (f b) => Maybe a -> WithOptional f b Source #

WithOptional smart constructor for the special case of optional values that are representationally equivalent to some "wrapper" type.

For example: withOptional @HeaderTransformsAction headers == WithOptional $ fmap HeadersTransform headers

In other words: this function observes the isomorphism between Maybe a and WithOptional f b if an isomorphism exists between a and f b.

data ResponseTransform Source #

A set of data transformation functions generated from a MetadataResponseTransform. Nothing means use the original response value.

data MetadataResponseTransform Source #

Instances

Instances details
Eq MetadataResponseTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Show MetadataResponseTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Generic MetadataResponseTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Associated Types

type Rep MetadataResponseTransform :: Type -> Type #

NFData MetadataResponseTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

FromJSON MetadataResponseTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Methods

parseJSON :: Value -> Parser MetadataResponseTransform

parseJSONList :: Value -> Parser [MetadataResponseTransform]

ToJSON MetadataResponseTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

Cacheable MetadataResponseTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

type Rep MetadataResponseTransform Source # 
Instance details

Defined in Hasura.RQL.DDL.Webhook.Transform

type Rep MetadataResponseTransform = D1 ('MetaData "MetadataResponseTransform" "Hasura.RQL.DDL.Webhook.Transform" "graphql-engine-1.0.0-inplace" 'False) (C1 ('MetaCons "MetadataResponseTransform" 'PrefixI 'True) (S1 ('MetaSel ('Just "mrtVersion") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedStrict) (Rec0 Version) :*: (S1 ('MetaSel ('Just "mrtBodyTransform") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedStrict) (Rec0 (Maybe BodyTransformFn)) :*: S1 ('MetaSel ('Just "mrtTemplatingEngine") 'NoSourceUnpackedness 'NoSourceStrictness 'DecidedStrict) (Rec0 TemplatingEngine))))

mkRespTemplateTransform :: TemplatingEngine -> BodyTransformFn -> ResponseTransformCtx -> Either TransformErrorBundle Value Source #

Construct a Template Transformation function for Responses

XXX: This function makes internal usage of decodeUtf8, which throws an impure exception when the supplied ByteString cannot be decoded into valid UTF8 text!

applyResponseTransform :: ResponseTransform -> ResponseTransformCtx -> Either TransformErrorBundle ByteString Source #

At the moment we only transform the body of Responses. 'http-client' does not export the constructors for Response. If we want to transform then we will need additional apply functions.