It’s response is {:ok, %{data: %{}}}
.
It does work properly with the following mutations:
mutation CreateUser($username: String!, $password: String!) {
createUser(username: $username, password: $password) {
id
}
}
mutation CreateSession($username: String!, $password: String!) {
createSession(username: $username, password: $password) {
token
}
}
schema/types.ex
defmodule Web.Schema.Types do
use Absinthe.Schema.Notation
@desc "a user"
object :user do
field :id, :id
field :username, :string
end
@desc "a session"
object :session do
field :token, :string
end
end
resolver/user.ex
btw what’s a better way to translate changeset errors?
defmodule Web.Resolver.User do
def create(_parent, user_params, _info) do
case Users.insert(user_params) do
{:ok, user} ->
{:ok, user}
{:error, changeset} ->
{:error, translate(changeset.errors)}
end
end
defp translate(errors) do
errors
|> Enum.map(fn {key, {value, _}} -> "#{key} #{value}" end)
|> Enum.join()
end
end
resolver/session.ex
defmodule Web.Resolver.Session do
import Comeonin.Bcrypt, only: [checkpw: 2, dummy_checkpw: 0]
def create(_parent, %{username: username, password: password}, _info) do
case verify(username, password) do
{:ok, token} ->
{:ok, %{token: token}}
{:error, msg} ->
{:error, "Incorrect login credentials"}
end
end
defp verify(username, given_password) do
user = Users.get_by(username: username)
cond do
user && checkpw(given_password, user.password_hash) ->
token = Phoenix.Token.sign(Web.Endpoint, "user", user.id)
{:ok, token}
user ->
{:error, :unauthorized}
true ->
dummy_checkpw()
{:error, :not_found}
end
end
end
schema.ex
defmodule Web.Schema do
use Absinthe.Schema
alias Web.Resolver.{User, Session}
import_types Web.Schema.Types
mutation do
field :create_user, type: :user do
arg :username, non_null(:string)
arg :password, non_null(:string)
resolve &User.create/3
end
field :create_session, type: :session do
arg :username, non_null(:string)
arg :password, non_null(:string)
resolve &Session.create/3
end
end
end