morpheus-graphql-core-0.13.0: src/Data/Morpheus/Schema/Schema.hs
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE QuasiQuotes #-}
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE TemplateHaskell #-}
{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE TypeOperators #-}
module Data.Morpheus.Schema.Schema
( withSystemTypes,
systemTypes,
)
where
-- MORPHEUS
import Data.Morpheus.Internal.Utils
( (<:>),
singleton,
)
import Data.Morpheus.Schema.DSL (dsl)
import Data.Morpheus.Types.Internal.AST
( ANY,
DataFingerprint (..),
FieldsDefinition,
Message,
OUT,
Schema (..),
TypeContent (..),
TypeDefinition (..),
TypeUpdater,
TypeWrapper (..),
createArgument,
insertType,
internalFingerprint,
mkField,
mkObjectField,
unsafeFromFields,
)
import Data.Morpheus.Types.Internal.Resolving
( failure,
resolveUpdates,
)
withSystemTypes :: TypeUpdater
withSystemTypes s@Schema {query = q@TypeDefinition {typeContent = DataObject inter fields}} =
( do
fs <- fields <:> hiddenFields
pure $ s {query = q {typeContent = DataObject inter fs}}
)
>>= (`resolveUpdates` map (insertType . internalType) systemTypes)
withSystemTypes _ = failure ("Query must be an Object Type" :: Message)
hiddenFields :: FieldsDefinition OUT
hiddenFields =
unsafeFromFields
[ mkObjectField
(singleton (createArgument "name" ([], "String")))
"__type"
([TypeMaybe], "__Type"),
mkField
"__schema"
([], "__Schema")
]
internalType :: TypeDefinition a -> TypeDefinition a
internalType
tyDef@TypeDefinition
{ typeFingerprint = DataFingerprint name xs
} =
tyDef {typeFingerprint = internalFingerprint name xs}
systemTypes :: [TypeDefinition ANY]
systemTypes =
[dsl|
# default scalars
scalar Boolean
scalar Int
scalar Float
scalar String
scalar ID
type __Schema {
types: [__Type!]!
queryType: __Type!
mutationType: __Type
subscriptionType: __Type
directives: [__Directive!]!
}
type __Type {
kind: __TypeKind!
name: String
description: String
# OBJECT and INTERFACE only
fields(includeDeprecated: Boolean = false): [__Field!]
# OBJECT only
interfaces: [__Type!]
# INTERFACE and UNION only
possibleTypes: [__Type!]
# ENUM only
enumValues(includeDeprecated: Boolean = false): [__EnumValue!]
# INPUT_OBJECT only
inputFields: [__InputValue!]
# NON_NULL and LIST only
ofType: __Type
}
type __Field {
name: String!
description: String
args: [__InputValue!]!
type: __Type!
isDeprecated: Boolean!
deprecationReason: String
}
type __InputValue {
name: String!
description: String
type: __Type!
defaultValue: String
}
type __EnumValue {
name: String!
description: String
isDeprecated: Boolean!
deprecationReason: String
}
type __Directive {
name: String!
description: String
locations: [__DirectiveLocation!]!
args: [__InputValue!]!
}
enum __DirectiveLocation {
QUERY
MUTATION
SUBSCRIPTION
FIELD
FRAGMENT_DEFINITION
FRAGMENT_SPREAD
INLINE_FRAGMENT
SCHEMA
SCALAR
OBJECT
FIELD_DEFINITION
ARGUMENT_DEFINITION
INTERFACE
UNION
ENUM
ENUM_VALUE
INPUT_OBJECT
INPUT_FIELD_DEFINITION
}
enum __TypeKind {
SCALAR
OBJECT
INTERFACE
UNION
ENUM
INPUT_OBJECT
LIST
NON_NULL
}
|]