Current section
Files
Jump to
Current section
Files
lib/brains.ex
defmodule Brains do
@moduledoc """
`Brains` is a GraphQL client for Elixir on top of `Tesla`.
## Usage
```elixir
iex> connection = Brains.Connection.new("https://example.com/graph")
iex> Brains.query(connection, \"""
{
films {
title
}
}
\"""
)
{:ok,
%Tesla.Env{
body: "{\\"data\\":{\\"films\\":[{\\"title\\":\\"A New Hope\\"}]}}",
status: 200,
headers: []
}}
```
You can also run mutations:
```elixir
iex> Brains.query(connection, \"""
mutation createUser($name: String!) {
createUser(name: $name) {
id
name
}
}
\""",
variables: %{name: "uesteibar"}
)
```
"""
alias Brains.{Connection, Request}
@type connection :: Tesla.Client.t()
@type query_string :: String.t()
@type headers :: [header]
@type header :: {String.t(), String.t()}
@type options :: [option]
@type option :: {:operation_name, String.t()} | {:variables, map} | {:headers, headers}
@doc """
Runs a query request to your graphql endpoint.
## Example
```elixir
Brains.query(connection, \"""
{
films {
count
}
}
\""")
```
You can also pass variables for your query:
```elixir
Brains.query(connection, \"""
mutation createUser($name: String!) {
createUser(name: $name) {
id
name
}
}
\""",
variables: %{name: "uesteibar"}
)
```
"""
@spec query(
connection,
query_string :: map() | String.t(),
options :: keyword()
) ::
{:ok, map}
| {:error, reason :: term}
def query(connection, query_string, options \\ [])
when is_binary(query_string) and is_list(options) do
body = %{
"query" => query_string
}
body =
case Keyword.get(options, :operation_name) do
nil -> body
name -> Map.put(body, "operationName", name)
end
body =
case Keyword.get(options, :variables) do
nil -> body
variables -> Map.put(body, "variables", variables)
end
request =
Request.new()
|> Request.method(:post)
|> Request.add_param(:header, "content-type", "application/json")
|> Request.add_param(:body, :body, body |> Poison.encode!())
request =
case Keyword.get(options, :headers) do
nil ->
request
headers ->
Enum.reduce(headers, request, fn {key, value}, req ->
Request.add_param(req, :headers, key, value)
end)
end
connection
|> Connection.execute(request)
end
end