Absinthe Constraints
An absinthe library to add type constraints to your GraphQL schema using directives.
Installation
Install from Hex.pm
def deps do
[
{:absinthe_constraints, "~> 0.3.0"}
]
endUsage
1. Add use AbsintheConstraints to your schema
defmodule MyAppWeb.Schema do
use Absinthe.Schema
use AbsintheConstraints
# Use `import_sdl`, etc...
end
This registers the @constraints directive both for runtime validation
and as a directive declaration in the schema's blueprint. The
declaration is then included in mix absinthe.schema.sdl output, so the
generated SDL is valid GraphQL that downstream tooling (e.g.
graphql-inspector, graphql-js) can parse.
Older versions of this library recommended setting
@prototype_schema AbsintheConstraints.Directivedirectly. That still works at runtime but omits the directive declaration from SDL output, producing invalid GraphQL. Preferuse AbsintheConstraints.
2. Add the document phase to your absinthe Pipeline
Example using Absinthe.Plug:
# Somewhere in your router
def my_pipeline(config, opts) do
config
|> Absinthe.Plug.default_pipeline(opts)
|> AbsintheConstraints.Phase.add_to_pipeline(opts)
end
forward("/", Absinthe.Plug, schema: MyAppWeb.Schema, pipeline: {__MODULE__, :my_pipeline})3. Add constraints to your schema
# Somewhere in your schema
# Adding constraints to input object's fields
input_object :coordinates do
field(:latitude, non_null(:float), directives: [constraints: [min: -90, max: 90]])
field(:longitude, non_null(:float), directives: [constraints: [min: -180, max: 180]])
end
# Adding constraints to query field's arguments
object :my_queries do
field :my_field, non_null(:string) do
arg(:id, non_null(:string), directives: [constraints: [format: "uuid"]])
resolve(&my_resolver/2)
end
endSupported constraints
String
min_length
directives: [constraints: [min_length: 5]]
Restrict to a minimum length
max_length
directives: [constraints: [max_length: 5]]
Restrict to a maximum length
format
directives: [constraints: [format: "uuid"]]
Ensure value is in a particular format
Supported formats:
"uuid"- uses :elixir_uuid to validate the value"email"- uses a regex to validate the value
pattern
directives: [constraints: [pattern: "^[A-Z][0-9a-z]*$"]]
Ensure value follows a specific Regex pattern
Number (integer/float)
min
directives: [constraints: [min: 5]]
Ensure value is greater than or equal to
max
directives: [constraints: [max: 5]]
Ensure value is less than or equal to
List
min_items
directives: [constraints: [min_items: 5]]
Restrict to a minimum number of items
max_items
directives: [constraints: [max_items: 5]]
Restrict to a maximum number of items