Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language...
Transcript of Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language...
![Page 1: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/1.jpg)
Functional APIs with GraphQL & ElixirCODE BEAM LITE BERLIN 2018
![Page 2: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/2.jpg)
About me● Hubert Łępicki● @hubertlepicki● https://www.amberbit.com● Białystok, Poland
![Page 3: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/3.jpg)
☕
![Page 4: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/4.jpg)
![Page 5: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/5.jpg)
![Page 6: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/6.jpg)
The history behind it (educated guess)● Frontend: “We need list of posts with thumbnails and short text”● Back end: “Ok”● Frontend: “We need to make thumbnail fetching optional and need author
info”● Back end: “Ok”● Frontend: “We need optional list of comments with each post”● Back end: “You are ruining my API but okay”● Frontend: “We need….”
![Page 7: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/7.jpg)
![Page 8: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/8.jpg)
![Page 9: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/9.jpg)
![Page 10: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/10.jpg)
Born in 2012
![Page 11: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/11.jpg)
![Page 12: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/12.jpg)
![Page 13: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/13.jpg)
Made public in 2015
![Page 14: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/14.jpg)
What is this GraphQL thing?● Graph Query Language● Specification https://facebook.github.io/graphql● Describes how you query the data you want to retrieve● Describes how you modify the data● Describes how you get notified on data changes● Transport-independent● Usually used via HTTP API● Can be used over WebSocket● Can be used over custom transports● Can be used within application internally
![Page 15: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/15.jpg)
GraphQL in Elixir● Absinthe GraphQL Toolkit https://absinthe-graphql.org/● One of most complete GraphQL server-side specification implementations● Modular “toolkit” architecture, consisting of many small repositories (absinthe,
absinthe_plug etc.)● Actively worked on & maintained● Actively used in production● Good match (esp. subscriptions)● Sorts out some architectural design problems for your apps for you
![Page 16: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/16.jpg)
Time for some examples!
![Page 17: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/17.jpg)
Our database
User
Role
Project
Task
Assignment
Plug.Auth sets @conn.me to %User{id:1, email:”hubert…}
![Page 18: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/18.jpg)
How does it look like?doc = “””query { me { id, email }}”””
![Page 19: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/19.jpg)
How does it look like?doc = “””query { me { email, projects { id, name } }}”””
![Page 20: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/20.jpg)
How does it look like?doc = “””query { me { email, projects { id, tasks { id, name, completed } } }}”””
![Page 21: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/21.jpg)
How does it look like?doc = “””query { me { email, projects { id, tasks(matching: “deploy”) { id, name } } }}”””
![Page 22: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/22.jpg)
How does it look like?doc = “””query { me { tasks(completed: false) { id, name } }}”””
![Page 23: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/23.jpg)
How does it look like?Absinthe.run(doc, MyApp.Schema, context: %{})
=> {:ok, %{data: … }}
=> {:error, errors}
![Page 24: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/24.jpg)
How does it look like?%{data: %{ "me" => %{ "email" => "[email protected]", "projects" => [ %{"id" => 1, "tasks" => [ %{"id" => "1", "name" => "Deploy to staging"}, %{"id" => "2", "name" => "Deploy to production"}
]}]}}}
![Page 25: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/25.jpg)
Computed fieldsquery { me { projects { id, name, completed_percents } }}
![Page 26: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/26.jpg)
Computed fields%{data: %{ "me" => %{ "projects" => [ %{"id" => 1, "name" => “Conquering the World”, “completed_percents” => 99 }]}}}
![Page 27: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/27.jpg)
Let’s get our hands dirty!# mix.exs...defp deps do [ ... {:absinthe_phoenix, “~> 1.4”} ]end
➜ my_app git:(master) ✗ mix deps.getResolving Hex dependencies...Dependency resolution completed: absinthe 1.4.13 absinthe_phoenix 1.4.3...
![Page 28: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/28.jpg)
Let’s get our hands dirty!# lib/my_app_web/endpoint.exdefmodule MyAppWeb.Endpoint do use Phoenix.Endpoint, otp_app: :my_app use Absinthe.Phoenix.Endpoint ...
# lib/my_app/application.ex ... supervisor(MyAppWeb.Endpoint, []), supervisor(Absinthe.Subscription, [MyAppWeb.Endpoint]) ...
![Page 29: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/29.jpg)
Let’s get our hands dirty!# lib/my_app_web/channels/user_socket.exdefmodule MyAppWeb.UserSocket do use Phoenix.Socket use Absinthe.Phoenix.Socket, schema: MyAppWeb.Schema ...
![Page 30: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/30.jpg)
Let’s get our hands dirty!# lib/my_app_web/router.ex ... forward("/api/graphiql", Absinthe.Plug.GraphiQL, schema: MyApp.Schema, interface: :advanced) scope “/api” do pipe_through(:api) forward(“/”, Absinthe.Plug, schema: MyApp.Schema) end ...
![Page 31: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/31.jpg)
Describe your API with Schema# lib/my_app/schema.ex
defmodule MyApp.Schema do use Absinthe.Schema
# list objects ... # list queries & mutations ...end
![Page 32: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/32.jpg)
Sad news for you● GraphQL is Object-Oriented● ...or not really :)
![Page 33: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/33.jpg)
Objects● Compound types, consisting of one or more fields● Used for nodes in graph● RootQueryType● Me (or maybe User?)● Project● Task
![Page 34: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/34.jpg)
Scalars● Boolean● Float● ID● Int● String
● Absinthe-specific: :datetime, :naive_datetime, :date, :time, :decimal
![Page 35: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/35.jpg)
Scalarsscalar :my_date do parse fn input -> case Date.from_iso8601(input.value) do {:ok, date} -> {:ok, date} _ -> :error end end
serialize fn date -> Date.to_iso8601(date) endend* example from Craft GraphQL APIs in Elixir with Absinthe
![Page 36: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/36.jpg)
Types in GraphQL● Objects● Scalars● (and more… Unions, Interfaces, Enumerations...)
![Page 37: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/37.jpg)
...but where is the graph?
![Page 38: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/38.jpg)
The Graph & The Query
me
projects
RootQueryType
Me
Project
Task
tasks
query { me { email, projects { id, tasks(matching: “deploy”) { id, name, completed } } }}
![Page 39: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/39.jpg)
The Graph & The Schema
RootQueryType
Me
Project
me
projects
Task
tasks
defmodule MyApp.Schema use Absinthe.Schema
object :me do field :id, non_null(:string) field :name, non_null(:string) field :email, non_null(:string) field :avatar_url, :string
field :projects, list_of(:project) end ...end
![Page 40: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/40.jpg)
The Graph & The Schema
RootQueryType
Me
Project
me
projects
Task
tasks
object :project do field :id, non_null(:id) field :name, non_null(:string) field :tasks, list_of(:task) do @desc “Searches tasks by string” arg :matching, :string end @desc “Computed on the fly!” field :completed_percents, :integerend
![Page 41: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/41.jpg)
The Graph & The Schema
RootQueryType
Me
Project
me
projects
Task
tasks
object :task do field :id, non_null(:id) field :name, :string field :completed, non_null(:boolean)end
![Page 42: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/42.jpg)
The Graph & The Response
RootQueryType
Me
Project
me
projects
Task
tasks
%{data: %{ "me" => %{ "email" => "[email protected]", "projects" => [ %{"id" => 1, "tasks" => [ %{"name" => "Deploy to staging"}, %{"name" => "Deploy to prod"}
]}]}}}
![Page 43: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/43.jpg)
Schema design
RootQueryType
User
Project
me
projects
Task
tasks
Assignment
Role
owner
![Page 44: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/44.jpg)
Schema design
RootQueryType
Me
Project
me
projects
Task
tasks
AssignedUserassigned_users
UserProfile
ProjectMemberproject_members
tasks
UserProfile fields + role
email, name, avatar_url
![Page 45: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/45.jpg)
lib/my_app/schema.exdefmodule MyApp.Schema do use Absinthe.Schema
object :me do field :id, non_null(:string) field :name, non_null(:string) field :email, non_null(:string) field :avatar_url, :string field :projects, list_of(:project) field :tasks, list_of(:tasks) end ...
![Page 46: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/46.jpg)
lib/my_app/schema.ex ... object :project do field :id, non_null(:id) field :name, non_null(:string) field :tasks, list_of(:task) do arg :matching, :string end field :completed_percents, non_null(:integer) end ...
![Page 47: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/47.jpg)
lib/my_app/schema.ex ... object :task do field :id, non_null(:id) field :name, :string field :completed, non_null(:boolean) end
query do field :me, :me end end
![Page 48: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/48.jpg)
![Page 49: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/49.jpg)
lib/my_app/schema.ex ... query do field :me, :me do resolve fn _parent, _args, _resolution -> {:ok, %{id: 1, name: “Hubert Łępicki”, email: “[email protected]”, avatar_url: “http://example.com/hub.png”}} end end end end
![Page 50: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/50.jpg)
lib/my_app/schema.ex ... query do field :me, :me do resolve fn _parent, _args, _resolution -> {:ok, Repo.get(User, resolution.context.user_id)} end end end end
![Page 51: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/51.jpg)
![Page 52: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/52.jpg)
lib/my_app/schema.ex ... field :me, :me do resolve fn _parent, _args, _resolution -> {:ok, %{id: 1, name: “Hubert Łępicki”, email: “[email protected]”, avatar_url: “http://example.com/hub.png”, projects: [%{ id: 1, name: “First project”, tasks: [%{id: 1, name: “First task”}]
}]}} ...
![Page 53: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/53.jpg)
lib/my_app/schema.ex ... object :me do ... field :projects, list_of(:project) do resolve fn _parent, _args, _resolution -> {:ok, [ %{id: 1, name: "First project"} ]} end end end ...
![Page 54: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/54.jpg)
![Page 55: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/55.jpg)
lib/my_app/schema.ex...mutation do field :create_project, type: :project do arg :name, non_null(:string) resolve &Resolvers.Projects.create/3 endend...
![Page 56: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/56.jpg)
Phoenix integration@graphql """ query Index @action(mode: INTERNAL) { me @put { projects }}"""def index(conn, result) do render(conn, "index.html", projects: result.data.projects)end
![Page 57: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/57.jpg)
Problem #1: N+1 queries● can be reduced with smart schema design● cannot be avoided● can use `batch` with custom Project.by_ids function● can use Dataloader with Project, Task etc. as sources● ^^^ generate SQL IN(...) queries. One query per level.● can also preload data yourself in top-level resolvers● look ahead into `resolution.path` to see what’s been requested● use Ecto join + preload to load up data in single query
![Page 58: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/58.jpg)
Problem #2: We’re building DOS endpoint● Denial of Service● easy to craft queries that will attempt to load a lot of data● if you have loops in your schema, you are vulnerable
query {
me { projects{ name, users { email, projects { name, users { ...
![Page 59: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/59.jpg)
Problem #2: DOS prevention● absinthe has built-in query complexity analysis phase● give each field / edge complexity● sums up complexity of overall query● disallow queries with complexity > MAX_COMPLEXITY● timeouts & memory limits on resolver processes
![Page 60: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/60.jpg)
Problem #3: Caching● all queries go to POST /api● HTTP caching is easier with GET requests● client-side caching is easy (Apollo!) - need to provide & ask for IDs● server-side caching blow HTTP layer (in-app)● use Automatic Persisted Queries (APQ), sent via GET
![Page 61: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/61.jpg)
Problem #4: Hostile developer environments● JavaScript is bad but could be worse● Apollo is actually super awesome● Absinthe is equally super awesome● Not everyone is so lucky● Poor/incomplete/outdated implementations are common● Good Elixir GraphQL *client*?● Non-dynamic languages often require code generation (sigh)● Mobile app developers usually hate GraphQL (because of above)● Can use your GraphQL queries to build REST API if required (sigh)
![Page 62: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/62.jpg)
![Page 63: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/63.jpg)
Questions?
![Page 64: Functional APIs with GraphQL & Elixir · What is this GraphQL thing? Graph Query Language Specification Describes how you query the data you want to retrieve Describes how you modify](https://reader030.fdocuments.in/reader030/viewer/2022040100/5eca9852da6ae4659246739d/html5/thumbnails/64.jpg)
Thanks!