Change schema a bit
Closes #29 Signed-off-by: Thomas Citharel <tcit@tcit.fr>
This commit is contained in:
parent
403a32e996
commit
9f9113f094
|
@ -8,6 +8,12 @@ defenum(Mobilizon.Actors.ActorTypeEnum, :actor_type, [
|
||||||
:Service
|
:Service
|
||||||
])
|
])
|
||||||
|
|
||||||
|
defenum(Mobilizon.Actors.ActorOpennesssEnum, :openness, [
|
||||||
|
:invite_only,
|
||||||
|
:moderated,
|
||||||
|
:open
|
||||||
|
])
|
||||||
|
|
||||||
defmodule Mobilizon.Actors.Actor do
|
defmodule Mobilizon.Actors.Actor do
|
||||||
@moduledoc """
|
@moduledoc """
|
||||||
Represents an actor (local and remote actors)
|
Represents an actor (local and remote actors)
|
||||||
|
@ -42,6 +48,7 @@ defmodule Mobilizon.Actors.Actor do
|
||||||
field(:suspended, :boolean, default: false)
|
field(:suspended, :boolean, default: false)
|
||||||
field(:avatar_url, :string)
|
field(:avatar_url, :string)
|
||||||
field(:banner_url, :string)
|
field(:banner_url, :string)
|
||||||
|
# field(:openness, Mobilizon.Actors.ActorOpennesssEnum, default: :moderated)
|
||||||
many_to_many(:followers, Actor, join_through: Follower)
|
many_to_many(:followers, Actor, join_through: Follower)
|
||||||
has_many(:organized_events, Event, foreign_key: :organizer_actor_id)
|
has_many(:organized_events, Event, foreign_key: :organizer_actor_id)
|
||||||
many_to_many(:memberships, Actor, join_through: Member)
|
many_to_many(:memberships, Actor, join_through: Member)
|
||||||
|
|
|
@ -10,10 +10,12 @@ defmodule Mobilizon.Actors do
|
||||||
|
|
||||||
alias Mobilizon.Service.ActivityPub
|
alias Mobilizon.Service.ActivityPub
|
||||||
|
|
||||||
|
@doc false
|
||||||
def data() do
|
def data() do
|
||||||
Dataloader.Ecto.new(Repo, query: &query/2)
|
Dataloader.Ecto.new(Repo, query: &query/2)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@doc false
|
||||||
def query(queryable, _params) do
|
def query(queryable, _params) do
|
||||||
queryable
|
queryable
|
||||||
end
|
end
|
||||||
|
@ -312,14 +314,51 @@ defmodule Mobilizon.Actors do
|
||||||
if preload, do: Repo.preload(actor, [:followers]), else: actor
|
if preload, do: Repo.preload(actor, [:followers]), else: actor
|
||||||
end
|
end
|
||||||
|
|
||||||
def get_actor_by_name(name) do
|
@doc """
|
||||||
case String.split(name, "@") do
|
Get an actor by name
|
||||||
[name] ->
|
|
||||||
Repo.one(from(a in Actor, where: a.preferred_username == ^name and is_nil(a.domain)))
|
|
||||||
|
|
||||||
[name, domain] ->
|
## Examples
|
||||||
Repo.get_by(Actor, preferred_username: name, domain: domain)
|
iex> get_actor_by_name("tcit")
|
||||||
end
|
%Mobilizon.Actors.Actor{preferred_username: "tcit", domain: nil}
|
||||||
|
|
||||||
|
iex> get_actor_by_name("tcit@social.tcit.fr")
|
||||||
|
%Mobilizon.Actors.Actor{preferred_username: "tcit", domain: "social.tcit.fr"}
|
||||||
|
|
||||||
|
iex> get_actor_by_name("tcit", :Group)
|
||||||
|
nil
|
||||||
|
|
||||||
|
"""
|
||||||
|
@spec get_actor_by_name(String.t(), atom() | nil) :: Actor.t()
|
||||||
|
def get_actor_by_name(name, type \\ nil) do
|
||||||
|
# Base query
|
||||||
|
query = from(a in Actor)
|
||||||
|
|
||||||
|
# If we have Person / Group information
|
||||||
|
query =
|
||||||
|
if type in [:Person, :Group] do
|
||||||
|
from(a in query, where: a.type == ^type)
|
||||||
|
else
|
||||||
|
query
|
||||||
|
end
|
||||||
|
|
||||||
|
# If the name is a remote actor
|
||||||
|
query =
|
||||||
|
case String.split(name, "@") do
|
||||||
|
[name] -> do_get_actor_by_name(query, name)
|
||||||
|
[name, domain] -> do_get_actor_by_name(query, name, domain)
|
||||||
|
end
|
||||||
|
|
||||||
|
Repo.one(query)
|
||||||
|
end
|
||||||
|
|
||||||
|
# Get actor by username and domain is nil
|
||||||
|
defp do_get_actor_by_name(query, name) do
|
||||||
|
from(a in query, where: a.preferred_username == ^name and is_nil(a.domain))
|
||||||
|
end
|
||||||
|
|
||||||
|
# Get actor by username and domain
|
||||||
|
defp do_get_actor_by_name(query, name, domain) do
|
||||||
|
from(a in query, where: a.preferred_username == ^name and a.domain == ^domain)
|
||||||
end
|
end
|
||||||
|
|
||||||
def get_local_actor_by_name(name) do
|
def get_local_actor_by_name(name) do
|
||||||
|
@ -331,17 +370,11 @@ defmodule Mobilizon.Actors do
|
||||||
Repo.preload(actor, :organized_events)
|
Repo.preload(actor, :organized_events)
|
||||||
end
|
end
|
||||||
|
|
||||||
def get_actor_by_name_with_everything(name) do
|
@spec get_actor_by_name_with_everything(String.t(), atom() | nil) :: Actor.t()
|
||||||
actor =
|
def get_actor_by_name_with_everything(name, type \\ nil) do
|
||||||
case String.split(name, "@") do
|
name
|
||||||
[name] ->
|
|> get_actor_by_name(type)
|
||||||
Repo.one(from(a in Actor, where: a.preferred_username == ^name and is_nil(a.domain)))
|
|> Repo.preload(:organized_events)
|
||||||
|
|
||||||
[name, domain] ->
|
|
||||||
Repo.one(from(a in Actor, where: a.preferred_username == ^name and a.domain == ^domain))
|
|
||||||
end
|
|
||||||
|
|
||||||
Repo.preload(actor, :organized_events)
|
|
||||||
end
|
end
|
||||||
|
|
||||||
def get_or_fetch_by_url(url, preload \\ false) do
|
def get_or_fetch_by_url(url, preload \\ false) do
|
||||||
|
@ -394,6 +427,7 @@ defmodule Mobilizon.Actors do
|
||||||
@doc """
|
@doc """
|
||||||
Find actors by their name or displayed name
|
Find actors by their name or displayed name
|
||||||
"""
|
"""
|
||||||
|
@spec find_actors_by_username_or_name(String.t(), integer(), integer()) :: list(Actor.t())
|
||||||
def find_actors_by_username_or_name(username, page \\ 1, limit \\ 10)
|
def find_actors_by_username_or_name(username, page \\ 1, limit \\ 10)
|
||||||
def find_actors_by_username_or_name("", _page, _limit), do: []
|
def find_actors_by_username_or_name("", _page, _limit), do: []
|
||||||
|
|
||||||
|
@ -418,6 +452,7 @@ defmodule Mobilizon.Actors do
|
||||||
end
|
end
|
||||||
|
|
||||||
@email_regex ~r/^[a-zA-Z0-9.!#$%&'*+\/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*$/
|
@email_regex ~r/^[a-zA-Z0-9.!#$%&'*+\/=?^_`{|}~-]+@[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*$/
|
||||||
|
@spec search(String.t()) :: {:ok, list(Actor.t())} | {:ok, []} | {:error, any()}
|
||||||
def search(name) do
|
def search(name) do
|
||||||
# find already saved accounts
|
# find already saved accounts
|
||||||
case find_actors_by_username_or_name(name) do
|
case find_actors_by_username_or_name(name) do
|
||||||
|
|
|
@ -23,7 +23,7 @@ defmodule Mobilizon.Events.Tag.TitleSlug do
|
||||||
nil ->
|
nil ->
|
||||||
slug
|
slug
|
||||||
|
|
||||||
_story ->
|
_tag ->
|
||||||
slug
|
slug
|
||||||
|> Mobilizon.Slug.increment_slug()
|
|> Mobilizon.Slug.increment_slug()
|
||||||
|> build_unique_slug(changeset)
|
|> build_unique_slug(changeset)
|
||||||
|
@ -51,8 +51,8 @@ defmodule Mobilizon.Events.Tag do
|
||||||
def changeset(%Tag{} = tag, attrs) do
|
def changeset(%Tag{} = tag, attrs) do
|
||||||
tag
|
tag
|
||||||
|> cast(attrs, [:title])
|
|> cast(attrs, [:title])
|
||||||
|> validate_required([:title])
|
|
||||||
|> TitleSlug.maybe_generate_slug()
|
|> TitleSlug.maybe_generate_slug()
|
||||||
|
|> validate_required([:title, :slug])
|
||||||
|> TitleSlug.unique_constraint()
|
|> TitleSlug.unique_constraint()
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -12,14 +12,40 @@ defmodule MobilizonWeb.Resolvers.Actor do
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@doc """
|
||||||
|
Find a person
|
||||||
|
"""
|
||||||
|
def find_person(_parent, %{preferred_username: name}, _resolution) do
|
||||||
|
case ActivityPub.find_or_make_person_from_nickname(name) do
|
||||||
|
{:ok, actor} ->
|
||||||
|
{:ok, actor}
|
||||||
|
|
||||||
|
_ ->
|
||||||
|
{:error, "Person with name #{name} not found"}
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
@doc """
|
||||||
|
Find a person
|
||||||
|
"""
|
||||||
|
def find_group(_parent, %{preferred_username: name}, _resolution) do
|
||||||
|
case ActivityPub.find_or_make_group_from_nickname(name) do
|
||||||
|
{:ok, actor} ->
|
||||||
|
{:ok, actor}
|
||||||
|
|
||||||
|
_ ->
|
||||||
|
{:error, "Group with name #{name} not found"}
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
@doc """
|
@doc """
|
||||||
Returns the current actor for the currently logged-in user
|
Returns the current actor for the currently logged-in user
|
||||||
"""
|
"""
|
||||||
def get_current_actor(_parent, _args, %{context: %{current_user: user}}) do
|
def get_current_person(_parent, _args, %{context: %{current_user: user}}) do
|
||||||
{:ok, Actors.get_actor_for_user(user)}
|
{:ok, Actors.get_actor_for_user(user)}
|
||||||
end
|
end
|
||||||
|
|
||||||
def get_current_actor(_parent, _args, _resolution) do
|
def get_current_person(_parent, _args, _resolution) do
|
||||||
{:error, "You need to be logged-in to view current actor"}
|
{:error, "You need to be logged-in to view current person"}
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -60,7 +60,7 @@ defmodule MobilizonWeb.Resolvers.User do
|
||||||
Mobilizon.Actors.Service.Activation.check_confirmation_token(token),
|
Mobilizon.Actors.Service.Activation.check_confirmation_token(token),
|
||||||
%Actor{} = actor <- Actors.get_actor_for_user(user),
|
%Actor{} = actor <- Actors.get_actor_for_user(user),
|
||||||
{:ok, token, _} <- MobilizonWeb.Guardian.encode_and_sign(user) do
|
{:ok, token, _} <- MobilizonWeb.Guardian.encode_and_sign(user) do
|
||||||
{:ok, %{token: token, user: user, actor: actor}}
|
{:ok, %{token: token, user: user, person: actor}}
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -3,8 +3,8 @@ defmodule MobilizonWeb.Schema do
|
||||||
|
|
||||||
import Absinthe.Resolution.Helpers, only: [dataloader: 1]
|
import Absinthe.Resolution.Helpers, only: [dataloader: 1]
|
||||||
alias Mobilizon.{Actors, Events}
|
alias Mobilizon.{Actors, Events}
|
||||||
alias Mobilizon.Actors.Actor
|
alias Mobilizon.Actors.{Actor, Follower, Member}
|
||||||
alias Mobilizon.Events.Event
|
alias Mobilizon.Events.{Event, Comment, Participant}
|
||||||
|
|
||||||
import_types(MobilizonWeb.Schema.Custom.UUID)
|
import_types(MobilizonWeb.Schema.Custom.UUID)
|
||||||
import_types(Absinthe.Type.Custom)
|
import_types(Absinthe.Type.Custom)
|
||||||
|
@ -12,18 +12,20 @@ defmodule MobilizonWeb.Schema do
|
||||||
|
|
||||||
alias MobilizonWeb.Resolvers
|
alias MobilizonWeb.Resolvers
|
||||||
|
|
||||||
@desc "An ActivityPub actor"
|
@desc """
|
||||||
object :actor do
|
Represents a person identity
|
||||||
|
"""
|
||||||
|
object :person do
|
||||||
|
interfaces([:actor])
|
||||||
|
field(:user, :user, description: "The user this actor is associated to")
|
||||||
|
|
||||||
|
field(:member_of, list_of(:member), description: "The list of groups this person is member of")
|
||||||
|
|
||||||
field(:url, :string, description: "The ActivityPub actor's URL")
|
field(:url, :string, description: "The ActivityPub actor's URL")
|
||||||
# We probably don't need all of that
|
|
||||||
# field(:outbox_url, :string, description: "The ActivityPub actor outbox_url")
|
|
||||||
# field(:inbox_url, :string)
|
|
||||||
# field(:following_url, :string)
|
|
||||||
# field(:followers_url, :string)
|
|
||||||
# field(:shared_inbox_url, :string)
|
|
||||||
field(:type, :actor_type, description: "The type of Actor (Person, Group,…)")
|
field(:type, :actor_type, description: "The type of Actor (Person, Group,…)")
|
||||||
field(:name, :string, description: "The actor's displayed name")
|
field(:name, :string, description: "The actor's displayed name")
|
||||||
field(:domain, :string, description: "The actor's domain if (null if it's this instance)")
|
field(:domain, :string, description: "The actor's domain if (null if it's this instance)")
|
||||||
|
field(:local, :boolean, description: "If the actor is from this instance")
|
||||||
field(:summary, :string, description: "The actor's summary")
|
field(:summary, :string, description: "The actor's summary")
|
||||||
field(:preferred_username, :string, description: "The actor's preferred username")
|
field(:preferred_username, :string, description: "The actor's preferred username")
|
||||||
field(:keys, :string, description: "The actors RSA Keys")
|
field(:keys, :string, description: "The actors RSA Keys")
|
||||||
|
@ -35,14 +37,126 @@ defmodule MobilizonWeb.Schema do
|
||||||
field(:suspended, :boolean, description: "If the actor is suspended")
|
field(:suspended, :boolean, description: "If the actor is suspended")
|
||||||
field(:avatar_url, :string, description: "The actor's avatar url")
|
field(:avatar_url, :string, description: "The actor's avatar url")
|
||||||
field(:banner_url, :string, description: "The actor's banner url")
|
field(:banner_url, :string, description: "The actor's banner url")
|
||||||
# field(:followers, list_of(:follower))
|
|
||||||
|
# These one should have a privacy setting
|
||||||
|
field(:following, list_of(:follower), description: "List of followings")
|
||||||
|
field(:followers, list_of(:follower), description: "List of followers")
|
||||||
|
field(:followersCount, :integer, description: "Number of followers for this actor")
|
||||||
|
field(:followingCount, :integer, description: "Number of actors following this actor")
|
||||||
|
|
||||||
|
# This one should have a privacy setting
|
||||||
|
field(:organized_events, list_of(:event),
|
||||||
|
resolve: dataloader(Events),
|
||||||
|
description: "A list of the events this actor has organized"
|
||||||
|
)
|
||||||
|
end
|
||||||
|
|
||||||
|
@desc """
|
||||||
|
Represents a group of actors
|
||||||
|
"""
|
||||||
|
object :group do
|
||||||
|
interfaces([:actor])
|
||||||
|
|
||||||
|
field(:url, :string, description: "The ActivityPub actor's URL")
|
||||||
|
field(:type, :actor_type, description: "The type of Actor (Person, Group,…)")
|
||||||
|
field(:name, :string, description: "The actor's displayed name")
|
||||||
|
field(:domain, :string, description: "The actor's domain if (null if it's this instance)")
|
||||||
|
field(:local, :boolean, description: "If the actor is from this instance")
|
||||||
|
field(:summary, :string, description: "The actor's summary")
|
||||||
|
field(:preferred_username, :string, description: "The actor's preferred username")
|
||||||
|
field(:keys, :string, description: "The actors RSA Keys")
|
||||||
|
|
||||||
|
field(:manually_approves_followers, :boolean,
|
||||||
|
description: "Whether the actors manually approves followers"
|
||||||
|
)
|
||||||
|
|
||||||
|
field(:suspended, :boolean, description: "If the actor is suspended")
|
||||||
|
field(:avatar_url, :string, description: "The actor's avatar url")
|
||||||
|
field(:banner_url, :string, description: "The actor's banner url")
|
||||||
|
|
||||||
|
# These one should have a privacy setting
|
||||||
|
field(:following, list_of(:follower), description: "List of followings")
|
||||||
|
field(:followers, list_of(:follower), description: "List of followers")
|
||||||
|
field(:followersCount, :integer, description: "Number of followers for this actor")
|
||||||
|
field(:followingCount, :integer, description: "Number of actors following this actor")
|
||||||
|
|
||||||
|
# This one should have a privacy setting
|
||||||
field(:organized_events, list_of(:event),
|
field(:organized_events, list_of(:event),
|
||||||
resolve: dataloader(Events),
|
resolve: dataloader(Events),
|
||||||
description: "A list of the events this actor has organized"
|
description: "A list of the events this actor has organized"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
field(:types, :group_type, description: "The type of group : Group, Community,…")
|
||||||
|
|
||||||
|
field(:openness, :openness,
|
||||||
|
description: "Whether the group is opened to all or has restricted access"
|
||||||
|
)
|
||||||
|
|
||||||
|
field(:members, non_null(list_of(:member)), description: "List of group members")
|
||||||
|
end
|
||||||
|
|
||||||
|
@desc """
|
||||||
|
Describes how an actor is opened to follows
|
||||||
|
"""
|
||||||
|
enum :openness do
|
||||||
|
value(:invite_only, description: "The actor can only be followed by invitation")
|
||||||
|
|
||||||
|
value(:moderated, description: "The actor needs to accept the following before it's effective")
|
||||||
|
|
||||||
|
value(:open, description: "The actor is open to followings")
|
||||||
|
end
|
||||||
|
|
||||||
|
@desc """
|
||||||
|
The types of Group that exist
|
||||||
|
"""
|
||||||
|
enum :group_type do
|
||||||
|
value(:group, description: "A private group of persons")
|
||||||
|
value(:community, description: "A public group of many actors")
|
||||||
|
end
|
||||||
|
|
||||||
|
@desc "An ActivityPub actor"
|
||||||
|
interface :actor do
|
||||||
|
field(:url, :string, description: "The ActivityPub actor's URL")
|
||||||
|
field(:type, :actor_type, description: "The type of Actor (Person, Group,…)")
|
||||||
|
field(:name, :string, description: "The actor's displayed name")
|
||||||
|
field(:domain, :string, description: "The actor's domain if (null if it's this instance)")
|
||||||
|
field(:local, :boolean, description: "If the actor is from this instance")
|
||||||
|
field(:summary, :string, description: "The actor's summary")
|
||||||
|
field(:preferred_username, :string, description: "The actor's preferred username")
|
||||||
|
field(:keys, :string, description: "The actors RSA Keys")
|
||||||
|
|
||||||
|
field(:manually_approves_followers, :boolean,
|
||||||
|
description: "Whether the actors manually approves followers"
|
||||||
|
)
|
||||||
|
|
||||||
|
field(:suspended, :boolean, description: "If the actor is suspended")
|
||||||
|
field(:avatar_url, :string, description: "The actor's avatar url")
|
||||||
|
field(:banner_url, :string, description: "The actor's banner url")
|
||||||
|
|
||||||
|
# These one should have a privacy setting
|
||||||
|
field(:following, list_of(:follower), description: "List of followings")
|
||||||
|
field(:followers, list_of(:follower), description: "List of followers")
|
||||||
|
field(:followersCount, :integer, description: "Number of followers for this actor")
|
||||||
|
field(:followingCount, :integer, description: "Number of actors following this actor")
|
||||||
|
|
||||||
|
# This one should have a privacy setting
|
||||||
|
field(:organized_events, list_of(:event),
|
||||||
|
resolve: dataloader(Events),
|
||||||
|
description: "A list of the events this actor has organized"
|
||||||
|
)
|
||||||
|
|
||||||
|
# This one is for the person itself **only**
|
||||||
|
# field(:feed, list_of(:event), description: "List of events the actor sees in his or her feed")
|
||||||
|
|
||||||
# field(:memberships, list_of(:member))
|
# field(:memberships, list_of(:member))
|
||||||
field(:user, :user, description: "The user this actor is associated to")
|
|
||||||
|
resolve_type(fn
|
||||||
|
%Actor{type: :Person}, _ ->
|
||||||
|
:person
|
||||||
|
|
||||||
|
%Actor{type: :Group}, _ ->
|
||||||
|
:group
|
||||||
|
end)
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "The list of types an actor can be"
|
@desc "The list of types an actor can be"
|
||||||
|
@ -58,11 +172,12 @@ defmodule MobilizonWeb.Schema do
|
||||||
object :user do
|
object :user do
|
||||||
field(:id, non_null(:id), description: "The user's ID")
|
field(:id, non_null(:id), description: "The user's ID")
|
||||||
field(:email, non_null(:string), description: "The user's email")
|
field(:email, non_null(:string), description: "The user's email")
|
||||||
# , resolve: dataloader(:actors))
|
|
||||||
field(:actors, non_null(list_of(:actor)),
|
field(:profiles, non_null(list_of(:person)),
|
||||||
description: "The user's list of actors (identities)"
|
description: "The user's list of profiles (identities)"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
# TODO: This shouldn't be an ID, but the actor itself
|
||||||
field(:default_actor_id, non_null(:integer), description: "The user's default actor")
|
field(:default_actor_id, non_null(:integer), description: "The user's default actor")
|
||||||
|
|
||||||
field(:confirmed_at, :datetime,
|
field(:confirmed_at, :datetime,
|
||||||
|
@ -86,89 +201,177 @@ defmodule MobilizonWeb.Schema do
|
||||||
|
|
||||||
@desc "A JWT and the associated user ID"
|
@desc "A JWT and the associated user ID"
|
||||||
object :login do
|
object :login do
|
||||||
field(:token, non_null(:string))
|
field(:token, non_null(:string), description: "A JWT Token for this session")
|
||||||
field(:user, non_null(:user))
|
field(:user, non_null(:user), description: "The user associated to this session")
|
||||||
field(:actor, non_null(:actor))
|
field(:person, non_null(:person), description: "The person associated to this session")
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "An event"
|
@desc "An event"
|
||||||
object :event do
|
object :event do
|
||||||
field(:uuid, :uuid)
|
field(:uuid, :uuid, description: "The Event UUID")
|
||||||
field(:url, :string)
|
field(:url, :string, description: "The ActivityPub Event URL")
|
||||||
field(:local, :boolean)
|
field(:local, :boolean, description: "Whether the event is local or not")
|
||||||
field(:title, :string)
|
field(:title, :string, description: "The event's title")
|
||||||
field(:description, :string)
|
field(:description, :string, description: "The event's description")
|
||||||
field(:begins_on, :datetime)
|
field(:begins_on, :datetime, description: "Datetime for when the event begins")
|
||||||
field(:ends_on, :datetime)
|
field(:ends_on, :datetime, description: "Datetime for when the event ends")
|
||||||
field(:state, :integer)
|
field(:state, :integer, description: "State of the event")
|
||||||
field(:status, :integer)
|
field(:status, :integer, description: "Status of the event")
|
||||||
field(:public, :boolean)
|
field(:public, :boolean, description: "Whether the event is public or not")
|
||||||
field(:thumbnail, :string)
|
# TODO replace me with picture object
|
||||||
field(:large_image, :string)
|
field(:thumbnail, :string, description: "A thumbnail picture for the event")
|
||||||
field(:publish_at, :datetime)
|
# TODO replace me with banner
|
||||||
field(:address_type, :address_type)
|
field(:large_image, :string, description: "A large picture for the event")
|
||||||
field(:online_address, :string)
|
field(:publish_at, :datetime, description: "When the event was published")
|
||||||
field(:phone, :string)
|
field(:address_type, :address_type, description: "The type of the event's address")
|
||||||
|
# TODO implement these properly with an interface
|
||||||
|
# field(:online_address, :string, description: "???")
|
||||||
|
# field(:phone, :string, description: "")
|
||||||
|
|
||||||
field :organizer_actor, :actor do
|
field(:organizer_actor, :person,
|
||||||
resolve(dataloader(Actors))
|
resolve: dataloader(Actors),
|
||||||
end
|
description: "The event's organizer (as a person)"
|
||||||
|
)
|
||||||
|
|
||||||
field(:attributed_to, :actor)
|
field(:attributed_to, :actor, description: "Who the event is attributed to (often a group)")
|
||||||
# field(:tags, list_of(:tag))
|
# field(:tags, list_of(:tag))
|
||||||
field(:category, :category)
|
field(:category, :category, description: "The event's category")
|
||||||
|
|
||||||
field(:participants, list_of(:participant),
|
field(:participants, list_of(:participant),
|
||||||
resolve: &Resolvers.Event.list_participants_for_event/3
|
resolve: &Resolvers.Event.list_participants_for_event/3,
|
||||||
|
description: "The event's participants"
|
||||||
)
|
)
|
||||||
|
|
||||||
# field(:tracks, list_of(:track))
|
# field(:tracks, list_of(:track))
|
||||||
# field(:sessions, list_of(:session))
|
# field(:sessions, list_of(:session))
|
||||||
# field(:physical_address, :address)
|
# field(:physical_address, :address)
|
||||||
|
|
||||||
field(:updated_at, :datetime)
|
field(:updated_at, :datetime, description: "When the event was last updated")
|
||||||
field(:created_at, :datetime)
|
field(:created_at, :datetime, description: "When the event was created")
|
||||||
|
end
|
||||||
|
|
||||||
|
@desc "A comment"
|
||||||
|
object :comment do
|
||||||
|
field(:uuid, :uuid)
|
||||||
|
field(:url, :string)
|
||||||
|
field(:local, :boolean)
|
||||||
|
field(:content, :string)
|
||||||
|
field(:primaryLanguage, :string)
|
||||||
|
field(:replies, list_of(:comment))
|
||||||
|
field(:threadLanguages, non_null(list_of(:string)))
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "Represents a participant to an event"
|
@desc "Represents a participant to an event"
|
||||||
object :participant do
|
object :participant do
|
||||||
# field(:event, :event, resolve: dataloader(Events))
|
field(:event, :event,
|
||||||
# , resolve: dataloader(Actors)
|
resolve: dataloader(Events),
|
||||||
field(:actor, :actor)
|
description: "The event which the actor participates in"
|
||||||
field(:role, :integer)
|
)
|
||||||
|
|
||||||
|
field(:actor, :actor, description: "The actor that participates to the event")
|
||||||
|
field(:role, :integer, description: "The role of this actor at this event")
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "The list of types an address can be"
|
@desc "The list of types an address can be"
|
||||||
enum :address_type do
|
enum :address_type do
|
||||||
value(:physical)
|
value(:physical, description: "The address is physical, like a postal address")
|
||||||
value(:url)
|
value(:url, description: "The address is on the Web, like an URL")
|
||||||
value(:phone)
|
value(:phone, description: "The address is a phone number for a conference")
|
||||||
value(:other)
|
value(:other, description: "The address is something else")
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "A category"
|
@desc "A category"
|
||||||
object :category do
|
object :category do
|
||||||
field(:id, :id)
|
field(:id, :id, description: "The category's ID")
|
||||||
field(:description, :string)
|
field(:description, :string, description: "The category's description")
|
||||||
field(:picture, :picture)
|
field(:picture, :picture, description: "The category's picture")
|
||||||
field(:title, :string)
|
field(:title, :string, description: "The category's title")
|
||||||
field(:updated_at, :datetime)
|
|
||||||
field(:created_at, :datetime)
|
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "A picture"
|
@desc "A picture"
|
||||||
object :picture do
|
object :picture do
|
||||||
field(:url, :string)
|
field(:url, :string, description: "The URL for this picture")
|
||||||
field(:url_thumbnail, :string)
|
field(:url_thumbnail, :string, description: "The URL for this picture's thumbnail")
|
||||||
|
end
|
||||||
|
|
||||||
|
@desc """
|
||||||
|
Represents a notification for an user
|
||||||
|
"""
|
||||||
|
object :notification do
|
||||||
|
field(:id, :integer, description: "The notification ID")
|
||||||
|
field(:user, :user, description: "The user to transmit the notification to")
|
||||||
|
field(:actor, :actor, description: "The notification target profile")
|
||||||
|
|
||||||
|
field(:activity_type, :integer,
|
||||||
|
description:
|
||||||
|
"Whether the notification is about a follow, group join, event change or comment"
|
||||||
|
)
|
||||||
|
|
||||||
|
field(:target_object, :object, description: "The object responsible for the notification")
|
||||||
|
field(:summary, :string, description: "Text inside the notification")
|
||||||
|
field(:seen, :boolean, description: "Whether or not the notification was seen by the user")
|
||||||
|
field(:published, :datetime, description: "Datetime when the notification was published")
|
||||||
|
end
|
||||||
|
|
||||||
|
@desc """
|
||||||
|
Represents a member of a group
|
||||||
|
"""
|
||||||
|
object :member do
|
||||||
|
field(:parent, :group, description: "Of which the profile is member")
|
||||||
|
field(:person, :person, description: "Which profile is member of")
|
||||||
|
field(:role, :integer, description: "The role of this membership")
|
||||||
|
field(:approved, :boolean, description: "Whether this membership has been approved")
|
||||||
|
end
|
||||||
|
|
||||||
|
@desc """
|
||||||
|
Represents an actor's follower
|
||||||
|
"""
|
||||||
|
object :follower do
|
||||||
|
field(:target_actor, :actor, description: "What or who the profile follows")
|
||||||
|
field(:actor, :actor, description: "Which profile follows")
|
||||||
|
|
||||||
|
field(:approved, :boolean,
|
||||||
|
description: "Whether the follow has been approved by the target actor"
|
||||||
|
)
|
||||||
|
end
|
||||||
|
|
||||||
|
union :object do
|
||||||
|
types([:event, :person, :group, :comment, :follower, :member, :participant])
|
||||||
|
|
||||||
|
resolve_type(fn
|
||||||
|
%Actor{type: :Person}, _ ->
|
||||||
|
:person
|
||||||
|
|
||||||
|
%Actor{type: :Group}, _ ->
|
||||||
|
:group
|
||||||
|
|
||||||
|
%Event{}, _ ->
|
||||||
|
:event
|
||||||
|
|
||||||
|
%Comment{}, _ ->
|
||||||
|
:comment
|
||||||
|
|
||||||
|
%Follower{}, _ ->
|
||||||
|
:follower
|
||||||
|
|
||||||
|
%Member{}, _ ->
|
||||||
|
:member
|
||||||
|
|
||||||
|
%Participant{}, _ ->
|
||||||
|
:participant
|
||||||
|
end)
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "A search result"
|
@desc "A search result"
|
||||||
union :search_result do
|
union :search_result do
|
||||||
types([:event, :actor])
|
types([:event, :person, :group])
|
||||||
|
|
||||||
resolve_type(fn
|
resolve_type(fn
|
||||||
%Actor{}, _ ->
|
%Actor{type: :Person}, _ ->
|
||||||
:actor
|
:person
|
||||||
|
|
||||||
|
%Actor{type: :Group}, _ ->
|
||||||
|
:group
|
||||||
|
|
||||||
%Event{}, _ ->
|
%Event{}, _ ->
|
||||||
:event
|
:event
|
||||||
|
@ -188,13 +391,16 @@ defmodule MobilizonWeb.Schema do
|
||||||
[Absinthe.Middleware.Dataloader | Absinthe.Plugin.defaults()]
|
[Absinthe.Middleware.Dataloader | Absinthe.Plugin.defaults()]
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@desc """
|
||||||
|
Root Query
|
||||||
|
"""
|
||||||
query do
|
query do
|
||||||
@desc "Get all events"
|
@desc "Get all events"
|
||||||
field :events, list_of(:event) do
|
field :events, list_of(:event) do
|
||||||
resolve(&Resolvers.Event.list_events/3)
|
resolve(&Resolvers.Event.list_events/3)
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "Search through events and actors"
|
@desc "Search through events, persons and groups"
|
||||||
field :search, list_of(:search_result) do
|
field :search, list_of(:search_result) do
|
||||||
arg(:search, non_null(:string))
|
arg(:search, non_null(:string))
|
||||||
arg(:page, :integer, default_value: 1)
|
arg(:page, :integer, default_value: 1)
|
||||||
|
@ -226,22 +432,25 @@ defmodule MobilizonWeb.Schema do
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "Get the current actor for the logged-in user"
|
@desc "Get the current actor for the logged-in user"
|
||||||
field :logged_actor, :actor do
|
field :logged_person, :person do
|
||||||
resolve(&Resolvers.Actor.get_current_actor/3)
|
resolve(&Resolvers.Actor.get_current_person/3)
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "Get an actor"
|
@desc "Get a person"
|
||||||
field :actor, :actor do
|
field :person, :person do
|
||||||
arg(:preferred_username, non_null(:string))
|
arg(:preferred_username, non_null(:string))
|
||||||
resolve(&Resolvers.Actor.find_actor/3)
|
resolve(&Resolvers.Actor.find_person/3)
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "Get the list of categories"
|
@desc "Get the list of categories"
|
||||||
field :categories, list_of(:category) do
|
field :categories, non_null(list_of(:category)) do
|
||||||
resolve(&Resolvers.Category.list_categories/3)
|
resolve(&Resolvers.Category.list_categories/3)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@desc """
|
||||||
|
Root Mutation
|
||||||
|
"""
|
||||||
mutation do
|
mutation do
|
||||||
@desc "Create an event"
|
@desc "Create an event"
|
||||||
field :create_event, type: :event do
|
field :create_event, type: :event do
|
||||||
|
@ -273,7 +482,7 @@ defmodule MobilizonWeb.Schema do
|
||||||
end
|
end
|
||||||
|
|
||||||
@desc "Create an user (returns an actor)"
|
@desc "Create an user (returns an actor)"
|
||||||
field :create_user, type: :actor do
|
field :create_user, type: :person do
|
||||||
arg(:email, non_null(:string))
|
arg(:email, non_null(:string))
|
||||||
arg(:password, non_null(:string))
|
arg(:password, non_null(:string))
|
||||||
arg(:username, non_null(:string))
|
arg(:username, non_null(:string))
|
||||||
|
|
|
@ -219,15 +219,21 @@ defmodule Mobilizon.Service.ActivityPub do
|
||||||
@doc """
|
@doc """
|
||||||
Find an actor in our local database or call Webfinger to find what's its AP ID is and then fetch it
|
Find an actor in our local database or call Webfinger to find what's its AP ID is and then fetch it
|
||||||
"""
|
"""
|
||||||
@spec find_or_make_actor_from_nickname(String.t()) :: tuple()
|
@spec find_or_make_actor_from_nickname(String.t(), atom() | nil) :: tuple()
|
||||||
def find_or_make_actor_from_nickname(nickname) do
|
def find_or_make_actor_from_nickname(nickname, type \\ nil) do
|
||||||
with %Actor{} = actor <- Actors.get_actor_by_name(nickname) do
|
with %Actor{} = actor <- Actors.get_actor_by_name(nickname, type) do
|
||||||
{:ok, actor}
|
{:ok, actor}
|
||||||
else
|
else
|
||||||
nil -> make_actor_from_nickname(nickname)
|
nil -> make_actor_from_nickname(nickname)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@spec find_or_make_person_from_nickname(String.t()) :: tuple()
|
||||||
|
def find_or_make_person_from_nickname(nick), do: find_or_make_actor_from_nickname(nick, :Person)
|
||||||
|
|
||||||
|
@spec find_or_make_group_from_nickname(String.t()) :: tuple()
|
||||||
|
def find_or_make_group_from_nickname(nick), do: find_or_make_actor_from_nickname(nick, :Group)
|
||||||
|
|
||||||
@doc """
|
@doc """
|
||||||
Create an actor inside our database from username, using Webfinger to find out it's AP ID and then fetch it
|
Create an actor inside our database from username, using Webfinger to find out it's AP ID and then fetch it
|
||||||
"""
|
"""
|
||||||
|
|
|
@ -306,7 +306,7 @@ defmodule Mobilizon.ActorsTest do
|
||||||
test "list_users/0 returns all users" do
|
test "list_users/0 returns all users" do
|
||||||
user = insert(:user)
|
user = insert(:user)
|
||||||
users = Actors.list_users()
|
users = Actors.list_users()
|
||||||
assert users == [user]
|
assert [user.id] == users |> Enum.map(& &1.id)
|
||||||
end
|
end
|
||||||
|
|
||||||
test "get_user!/1 returns the user with given id" do
|
test "get_user!/1 returns the user with given id" do
|
||||||
|
|
|
@ -48,12 +48,12 @@ defmodule Mobilizon.AddressesTest do
|
||||||
|
|
||||||
test "list_addresses/0 returns all addresses" do
|
test "list_addresses/0 returns all addresses" do
|
||||||
address = address_fixture()
|
address = address_fixture()
|
||||||
assert Addresses.list_addresses() == [address]
|
assert [address.id] == Addresses.list_addresses() |> Enum.map(& &1.id)
|
||||||
end
|
end
|
||||||
|
|
||||||
test "get_address!/1 returns the address with given id" do
|
test "get_address!/1 returns the address with given id" do
|
||||||
address = address_fixture()
|
address = address_fixture()
|
||||||
assert Addresses.get_address!(address.id) == address
|
assert Addresses.get_address!(address.id).id == address.id
|
||||||
end
|
end
|
||||||
|
|
||||||
test "create_address/1 with valid data creates a address" do
|
test "create_address/1 with valid data creates a address" do
|
||||||
|
@ -69,8 +69,7 @@ defmodule Mobilizon.AddressesTest do
|
||||||
|
|
||||||
test "update_address/2 with valid data updates the address" do
|
test "update_address/2 with valid data updates the address" do
|
||||||
address = address_fixture()
|
address = address_fixture()
|
||||||
assert {:ok, address} = Addresses.update_address(address, @update_attrs)
|
assert {:ok, %Address{} = address} = Addresses.update_address(address, @update_attrs)
|
||||||
assert %Address{} = address
|
|
||||||
assert address.addressCountry == "some updated addressCountry"
|
assert address.addressCountry == "some updated addressCountry"
|
||||||
assert address.addressLocality == "some updated addressLocality"
|
assert address.addressLocality == "some updated addressLocality"
|
||||||
assert address.addressRegion == "some updated addressRegion"
|
assert address.addressRegion == "some updated addressRegion"
|
||||||
|
|
|
@ -189,15 +189,15 @@ defmodule Mobilizon.EventsTest do
|
||||||
@invalid_attrs %{description: nil, picture: nil, title: nil}
|
@invalid_attrs %{description: nil, picture: nil, title: nil}
|
||||||
|
|
||||||
test "list_categories/0 returns all categories", %{category: category} do
|
test "list_categories/0 returns all categories", %{category: category} do
|
||||||
assert Events.list_categories() == [category]
|
assert [category.id] == Events.list_categories() |> Enum.map(& &1.id)
|
||||||
end
|
end
|
||||||
|
|
||||||
test "get_category!/1 returns the category with given id", %{category: category} do
|
test "get_category!/1 returns the category with given id", %{category: category} do
|
||||||
assert Events.get_category!(category.id) == category
|
assert Events.get_category!(category.id).id == category.id
|
||||||
end
|
end
|
||||||
|
|
||||||
test "get_category_by_title/1 return the category with given title", %{category: category} do
|
test "get_category_by_title/1 return the category with given title", %{category: category} do
|
||||||
assert Events.get_category_by_title(category.title) == category
|
assert Events.get_category_by_title(category.title).id == category.id
|
||||||
end
|
end
|
||||||
|
|
||||||
test "create_category/1 with valid data creates a category" do
|
test "create_category/1 with valid data creates a category" do
|
||||||
|
@ -212,8 +212,7 @@ defmodule Mobilizon.EventsTest do
|
||||||
end
|
end
|
||||||
|
|
||||||
test "update_category/2 with valid data updates the category", %{category: category} do
|
test "update_category/2 with valid data updates the category", %{category: category} do
|
||||||
assert {:ok, category} = Events.update_category(category, @update_attrs)
|
assert {:ok, %Category{} = category} = Events.update_category(category, @update_attrs)
|
||||||
assert %Category{} = category
|
|
||||||
assert category.description == "some updated description"
|
assert category.description == "some updated description"
|
||||||
assert category.picture.file_name == @update_attrs.picture.filename
|
assert category.picture.file_name == @update_attrs.picture.filename
|
||||||
assert category.title == "some updated title"
|
assert category.title == "some updated title"
|
||||||
|
@ -221,7 +220,7 @@ defmodule Mobilizon.EventsTest do
|
||||||
|
|
||||||
test "update_category/2 with invalid data returns error changeset", %{category: category} do
|
test "update_category/2 with invalid data returns error changeset", %{category: category} do
|
||||||
assert {:error, %Ecto.Changeset{}} = Events.update_category(category, @invalid_attrs)
|
assert {:error, %Ecto.Changeset{}} = Events.update_category(category, @invalid_attrs)
|
||||||
assert category == Events.get_category!(category.id)
|
assert category.description == Events.get_category!(category.id).description
|
||||||
end
|
end
|
||||||
|
|
||||||
test "delete_category/1 deletes the category", %{category: category} do
|
test "delete_category/1 deletes the category", %{category: category} do
|
||||||
|
@ -241,28 +240,24 @@ defmodule Mobilizon.EventsTest do
|
||||||
@update_attrs %{title: "some updated title"}
|
@update_attrs %{title: "some updated title"}
|
||||||
@invalid_attrs %{title: nil}
|
@invalid_attrs %{title: nil}
|
||||||
|
|
||||||
def tag_fixture(attrs \\ %{}) do
|
|
||||||
{:ok, tag} =
|
|
||||||
attrs
|
|
||||||
|> Enum.into(@valid_attrs)
|
|
||||||
|> Events.create_tag()
|
|
||||||
|
|
||||||
tag
|
|
||||||
end
|
|
||||||
|
|
||||||
test "list_tags/0 returns all tags" do
|
test "list_tags/0 returns all tags" do
|
||||||
tag = tag_fixture()
|
tag = insert(:tag)
|
||||||
assert Events.list_tags() == [tag]
|
assert [tag.id] == Events.list_tags() |> Enum.map(& &1.id)
|
||||||
end
|
end
|
||||||
|
|
||||||
test "get_tag!/1 returns the tag with given id" do
|
test "get_tag!/1 returns the tag with given id" do
|
||||||
tag = tag_fixture()
|
tag = insert(:tag)
|
||||||
assert Events.get_tag!(tag.id) == tag
|
assert Events.get_tag!(tag.id).id == tag.id
|
||||||
end
|
end
|
||||||
|
|
||||||
test "create_tag/1 with valid data creates a tag" do
|
test "create_tag/1 with valid data creates a tag" do
|
||||||
assert {:ok, %Tag{} = tag} = Events.create_tag(@valid_attrs)
|
assert {:ok, %Tag{} = tag} = Events.create_tag(@valid_attrs)
|
||||||
assert tag.title == "some title"
|
assert tag.title == "some title"
|
||||||
|
assert tag.slug == "some-title"
|
||||||
|
|
||||||
|
assert {:ok, %Tag{} = tag2} = Events.create_tag(@valid_attrs)
|
||||||
|
assert tag2.title == "some title"
|
||||||
|
assert tag2.slug == "some-title-1"
|
||||||
end
|
end
|
||||||
|
|
||||||
test "create_tag/1 with invalid data returns error changeset" do
|
test "create_tag/1 with invalid data returns error changeset" do
|
||||||
|
@ -270,26 +265,26 @@ defmodule Mobilizon.EventsTest do
|
||||||
end
|
end
|
||||||
|
|
||||||
test "update_tag/2 with valid data updates the tag" do
|
test "update_tag/2 with valid data updates the tag" do
|
||||||
tag = tag_fixture()
|
tag = insert(:tag)
|
||||||
assert {:ok, tag} = Events.update_tag(tag, @update_attrs)
|
assert {:ok, tag} = Events.update_tag(tag, @update_attrs)
|
||||||
assert %Tag{} = tag
|
assert %Tag{} = tag
|
||||||
assert tag.title == "some updated title"
|
assert tag.title == "some updated title"
|
||||||
end
|
end
|
||||||
|
|
||||||
test "update_tag/2 with invalid data returns error changeset" do
|
test "update_tag/2 with invalid data returns error changeset" do
|
||||||
tag = tag_fixture()
|
tag = insert(:tag)
|
||||||
assert {:error, %Ecto.Changeset{}} = Events.update_tag(tag, @invalid_attrs)
|
assert {:error, %Ecto.Changeset{}} = Events.update_tag(tag, @invalid_attrs)
|
||||||
assert tag == Events.get_tag!(tag.id)
|
assert tag.id == Events.get_tag!(tag.id).id
|
||||||
end
|
end
|
||||||
|
|
||||||
test "delete_tag/1 deletes the tag" do
|
test "delete_tag/1 deletes the tag" do
|
||||||
tag = tag_fixture()
|
tag = insert(:tag)
|
||||||
assert {:ok, %Tag{}} = Events.delete_tag(tag)
|
assert {:ok, %Tag{}} = Events.delete_tag(tag)
|
||||||
assert_raise Ecto.NoResultsError, fn -> Events.get_tag!(tag.id) end
|
assert_raise Ecto.NoResultsError, fn -> Events.get_tag!(tag.id) end
|
||||||
end
|
end
|
||||||
|
|
||||||
test "change_tag/1 returns a tag changeset" do
|
test "change_tag/1 returns a tag changeset" do
|
||||||
tag = tag_fixture()
|
tag = insert(:tag)
|
||||||
assert %Ecto.Changeset{} = Events.change_tag(tag)
|
assert %Ecto.Changeset{} = Events.change_tag(tag)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -405,26 +400,14 @@ defmodule Mobilizon.EventsTest do
|
||||||
videos_urls: nil
|
videos_urls: nil
|
||||||
}
|
}
|
||||||
|
|
||||||
def session_fixture(attrs \\ %{}) do
|
|
||||||
event = insert(:event)
|
|
||||||
valid_attrs = Map.put(@valid_attrs, :event_id, event.id)
|
|
||||||
|
|
||||||
{:ok, session} =
|
|
||||||
attrs
|
|
||||||
|> Enum.into(valid_attrs)
|
|
||||||
|> Events.create_session()
|
|
||||||
|
|
||||||
session
|
|
||||||
end
|
|
||||||
|
|
||||||
test "list_sessions/0 returns all sessions" do
|
test "list_sessions/0 returns all sessions" do
|
||||||
session = session_fixture()
|
session = insert(:session)
|
||||||
assert Events.list_sessions() == [session]
|
assert [session.id] == Events.list_sessions() |> Enum.map(& &1.id)
|
||||||
end
|
end
|
||||||
|
|
||||||
test "get_session!/1 returns the session with given id" do
|
test "get_session!/1 returns the session with given id" do
|
||||||
session = session_fixture()
|
session = insert(:session)
|
||||||
assert Events.get_session!(session.id) == session
|
assert Events.get_session!(session.id).id == session.id
|
||||||
end
|
end
|
||||||
|
|
||||||
test "create_session/1 with valid data creates a session" do
|
test "create_session/1 with valid data creates a session" do
|
||||||
|
@ -446,9 +429,8 @@ defmodule Mobilizon.EventsTest do
|
||||||
end
|
end
|
||||||
|
|
||||||
test "update_session/2 with valid data updates the session" do
|
test "update_session/2 with valid data updates the session" do
|
||||||
session = session_fixture()
|
session = insert(:session)
|
||||||
assert {:ok, session} = Events.update_session(session, @update_attrs)
|
assert {:ok, %Session{} = session} = Events.update_session(session, @update_attrs)
|
||||||
assert %Session{} = session
|
|
||||||
assert session.audios_urls == "some updated audios_urls"
|
assert session.audios_urls == "some updated audios_urls"
|
||||||
assert session.language == "some updated language"
|
assert session.language == "some updated language"
|
||||||
assert session.long_abstract == "some updated long_abstract"
|
assert session.long_abstract == "some updated long_abstract"
|
||||||
|
@ -460,19 +442,19 @@ defmodule Mobilizon.EventsTest do
|
||||||
end
|
end
|
||||||
|
|
||||||
test "update_session/2 with invalid data returns error changeset" do
|
test "update_session/2 with invalid data returns error changeset" do
|
||||||
session = session_fixture()
|
session = insert(:session)
|
||||||
assert {:error, %Ecto.Changeset{}} = Events.update_session(session, @invalid_attrs)
|
assert {:error, %Ecto.Changeset{}} = Events.update_session(session, @invalid_attrs)
|
||||||
assert session == Events.get_session!(session.id)
|
assert session.title == Events.get_session!(session.id).title
|
||||||
end
|
end
|
||||||
|
|
||||||
test "delete_session/1 deletes the session" do
|
test "delete_session/1 deletes the session" do
|
||||||
session = session_fixture()
|
session = insert(:session)
|
||||||
assert {:ok, %Session{}} = Events.delete_session(session)
|
assert {:ok, %Session{}} = Events.delete_session(session)
|
||||||
assert_raise Ecto.NoResultsError, fn -> Events.get_session!(session.id) end
|
assert_raise Ecto.NoResultsError, fn -> Events.get_session!(session.id) end
|
||||||
end
|
end
|
||||||
|
|
||||||
test "change_session/1 returns a session changeset" do
|
test "change_session/1 returns a session changeset" do
|
||||||
session = session_fixture()
|
session = insert(:session)
|
||||||
assert %Ecto.Changeset{} = Events.change_session(session)
|
assert %Ecto.Changeset{} = Events.change_session(session)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -488,26 +470,14 @@ defmodule Mobilizon.EventsTest do
|
||||||
}
|
}
|
||||||
@invalid_attrs %{color: nil, description: nil, name: nil}
|
@invalid_attrs %{color: nil, description: nil, name: nil}
|
||||||
|
|
||||||
def track_fixture(attrs \\ %{}) do
|
|
||||||
event = insert(:event)
|
|
||||||
valid_attrs = Map.put(@valid_attrs, :event_id, event.id)
|
|
||||||
|
|
||||||
{:ok, track} =
|
|
||||||
attrs
|
|
||||||
|> Enum.into(valid_attrs)
|
|
||||||
|> Events.create_track()
|
|
||||||
|
|
||||||
track
|
|
||||||
end
|
|
||||||
|
|
||||||
test "list_tracks/0 returns all tracks" do
|
test "list_tracks/0 returns all tracks" do
|
||||||
track = track_fixture()
|
track = insert(:track)
|
||||||
assert Events.list_tracks() == [track]
|
assert [track.id] == Events.list_tracks() |> Enum.map(& &1.id)
|
||||||
end
|
end
|
||||||
|
|
||||||
test "get_track!/1 returns the track with given id" do
|
test "get_track!/1 returns the track with given id" do
|
||||||
track = track_fixture()
|
track = insert(:track)
|
||||||
assert Events.get_track!(track.id) == track
|
assert Events.get_track!(track.id).id == track.id
|
||||||
end
|
end
|
||||||
|
|
||||||
test "create_track/1 with valid data creates a track" do
|
test "create_track/1 with valid data creates a track" do
|
||||||
|
@ -524,28 +494,27 @@ defmodule Mobilizon.EventsTest do
|
||||||
end
|
end
|
||||||
|
|
||||||
test "update_track/2 with valid data updates the track" do
|
test "update_track/2 with valid data updates the track" do
|
||||||
track = track_fixture()
|
track = insert(:track)
|
||||||
assert {:ok, track} = Events.update_track(track, @update_attrs)
|
{:ok, %Track{} = track} = Events.update_track(track, @update_attrs)
|
||||||
assert %Track{} = track
|
|
||||||
assert track.color == "some updated color"
|
assert track.color == "some updated color"
|
||||||
assert track.description == "some updated description"
|
assert track.description == "some updated description"
|
||||||
assert track.name == "some updated name"
|
assert track.name == "some updated name"
|
||||||
end
|
end
|
||||||
|
|
||||||
test "update_track/2 with invalid data returns error changeset" do
|
test "update_track/2 with invalid data returns error changeset" do
|
||||||
track = track_fixture()
|
track = insert(:track)
|
||||||
assert {:error, %Ecto.Changeset{}} = Events.update_track(track, @invalid_attrs)
|
assert {:error, %Ecto.Changeset{}} = Events.update_track(track, @invalid_attrs)
|
||||||
assert track == Events.get_track!(track.id)
|
assert track.color == Events.get_track!(track.id).color
|
||||||
end
|
end
|
||||||
|
|
||||||
test "delete_track/1 deletes the track" do
|
test "delete_track/1 deletes the track" do
|
||||||
track = track_fixture()
|
track = insert(:track)
|
||||||
assert {:ok, %Track{}} = Events.delete_track(track)
|
assert {:ok, %Track{}} = Events.delete_track(track)
|
||||||
assert_raise Ecto.NoResultsError, fn -> Events.get_track!(track.id) end
|
assert_raise Ecto.NoResultsError, fn -> Events.get_track!(track.id) end
|
||||||
end
|
end
|
||||||
|
|
||||||
test "change_track/1 returns a track changeset" do
|
test "change_track/1 returns a track changeset" do
|
||||||
track = track_fixture()
|
track = insert(:track)
|
||||||
assert %Ecto.Changeset{} = Events.change_track(track)
|
assert %Ecto.Changeset{} = Events.change_track(track)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
defmodule MobilizonWeb.Resolvers.ActorResolverTest do
|
defmodule MobilizonWeb.Resolvers.PersonResolverTest do
|
||||||
use MobilizonWeb.ConnCase
|
use MobilizonWeb.ConnCase
|
||||||
alias Mobilizon.Actors
|
alias Mobilizon.Actors
|
||||||
alias MobilizonWeb.AbsintheHelpers
|
alias MobilizonWeb.AbsintheHelpers
|
||||||
|
@ -6,13 +6,13 @@ defmodule MobilizonWeb.Resolvers.ActorResolverTest do
|
||||||
@valid_actor_params %{email: "test@test.tld", password: "testest", username: "test"}
|
@valid_actor_params %{email: "test@test.tld", password: "testest", username: "test"}
|
||||||
@non_existent_username "nonexistent"
|
@non_existent_username "nonexistent"
|
||||||
|
|
||||||
describe "Actor Resolver" do
|
describe "Person Resolver" do
|
||||||
test "find_actor/3 returns an actor by it's username", context do
|
test "find_actor/3 returns a person by it's username", context do
|
||||||
{:ok, actor} = Actors.register(@valid_actor_params)
|
{:ok, actor} = Actors.register(@valid_actor_params)
|
||||||
|
|
||||||
query = """
|
query = """
|
||||||
{
|
{
|
||||||
actor(preferredUsername: "#{actor.preferred_username}") {
|
person(preferredUsername: "#{actor.preferred_username}") {
|
||||||
preferredUsername,
|
preferredUsername,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -20,14 +20,14 @@ defmodule MobilizonWeb.Resolvers.ActorResolverTest do
|
||||||
|
|
||||||
res =
|
res =
|
||||||
context.conn
|
context.conn
|
||||||
|> get("/api", AbsintheHelpers.query_skeleton(query, "actor"))
|
|> get("/api", AbsintheHelpers.query_skeleton(query, "person"))
|
||||||
|
|
||||||
assert json_response(res, 200)["data"]["actor"]["preferredUsername"] ==
|
assert json_response(res, 200)["data"]["person"]["preferredUsername"] ==
|
||||||
actor.preferred_username
|
actor.preferred_username
|
||||||
|
|
||||||
query = """
|
query = """
|
||||||
{
|
{
|
||||||
actor(preferredUsername: "#{@non_existent_username}") {
|
person(preferredUsername: "#{@non_existent_username}") {
|
||||||
preferredUsername,
|
preferredUsername,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -35,20 +35,20 @@ defmodule MobilizonWeb.Resolvers.ActorResolverTest do
|
||||||
|
|
||||||
res =
|
res =
|
||||||
context.conn
|
context.conn
|
||||||
|> get("/api", AbsintheHelpers.query_skeleton(query, "actor"))
|
|> get("/api", AbsintheHelpers.query_skeleton(query, "person"))
|
||||||
|
|
||||||
assert json_response(res, 200)["data"]["actor"] == nil
|
assert json_response(res, 200)["data"]["person"] == nil
|
||||||
|
|
||||||
assert hd(json_response(res, 200)["errors"])["message"] ==
|
assert hd(json_response(res, 200)["errors"])["message"] ==
|
||||||
"Actor with name #{@non_existent_username} not found"
|
"Person with name #{@non_existent_username} not found"
|
||||||
end
|
end
|
||||||
|
|
||||||
test "get_current_actor/3 returns the current logged-in actor", context do
|
test "get_current_person/3 returns the current logged-in actor", context do
|
||||||
{:ok, actor} = Actors.register(@valid_actor_params)
|
{:ok, actor} = Actors.register(@valid_actor_params)
|
||||||
|
|
||||||
query = """
|
query = """
|
||||||
{
|
{
|
||||||
loggedActor {
|
loggedPerson {
|
||||||
avatarUrl,
|
avatarUrl,
|
||||||
preferredUsername,
|
preferredUsername,
|
||||||
}
|
}
|
||||||
|
@ -57,19 +57,19 @@ defmodule MobilizonWeb.Resolvers.ActorResolverTest do
|
||||||
|
|
||||||
res =
|
res =
|
||||||
context.conn
|
context.conn
|
||||||
|> get("/api", AbsintheHelpers.query_skeleton(query, "logged_actor"))
|
|> get("/api", AbsintheHelpers.query_skeleton(query, "logged_person"))
|
||||||
|
|
||||||
assert json_response(res, 200)["data"]["loggedActor"] == nil
|
assert json_response(res, 200)["data"]["loggedPerson"] == nil
|
||||||
|
|
||||||
assert hd(json_response(res, 200)["errors"])["message"] ==
|
assert hd(json_response(res, 200)["errors"])["message"] ==
|
||||||
"You need to be logged-in to view current actor"
|
"You need to be logged-in to view current person"
|
||||||
|
|
||||||
res =
|
res =
|
||||||
context.conn
|
context.conn
|
||||||
|> auth_conn(actor.user)
|
|> auth_conn(actor.user)
|
||||||
|> get("/api", AbsintheHelpers.query_skeleton(query, "logged_actor"))
|
|> get("/api", AbsintheHelpers.query_skeleton(query, "logged_person"))
|
||||||
|
|
||||||
assert json_response(res, 200)["data"]["loggedActor"]["preferredUsername"] ==
|
assert json_response(res, 200)["data"]["loggedPerson"]["preferredUsername"] ==
|
||||||
actor.preferred_username
|
actor.preferred_username
|
||||||
end
|
end
|
||||||
end
|
end
|
|
@ -140,7 +140,7 @@ defmodule MobilizonWeb.Resolvers.UserResolverTest do
|
||||||
user {
|
user {
|
||||||
id
|
id
|
||||||
},
|
},
|
||||||
actor {
|
person {
|
||||||
preferredUsername
|
preferredUsername
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -151,7 +151,7 @@ defmodule MobilizonWeb.Resolvers.UserResolverTest do
|
||||||
context.conn
|
context.conn
|
||||||
|> post("/api", AbsintheHelpers.mutation_skeleton(mutation))
|
|> post("/api", AbsintheHelpers.mutation_skeleton(mutation))
|
||||||
|
|
||||||
assert json_response(res, 200)["data"]["validateUser"]["actor"]["preferredUsername"] ==
|
assert json_response(res, 200)["data"]["validateUser"]["person"]["preferredUsername"] ==
|
||||||
@valid_actor_params.username
|
@valid_actor_params.username
|
||||||
|
|
||||||
assert json_response(res, 200)["data"]["validateUser"]["user"]["id"] ==
|
assert json_response(res, 200)["data"]["validateUser"]["user"]["id"] ==
|
||||||
|
@ -170,7 +170,7 @@ defmodule MobilizonWeb.Resolvers.UserResolverTest do
|
||||||
user {
|
user {
|
||||||
id
|
id
|
||||||
},
|
},
|
||||||
actor {
|
person {
|
||||||
preferredUsername
|
preferredUsername
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -53,6 +53,13 @@ defmodule Mobilizon.Factory do
|
||||||
}
|
}
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def tag_factory do
|
||||||
|
%Mobilizon.Events.Tag{
|
||||||
|
title: "MyTag",
|
||||||
|
slug: sequence("MyTag")
|
||||||
|
}
|
||||||
|
end
|
||||||
|
|
||||||
def address_factory do
|
def address_factory do
|
||||||
%Mobilizon.Addresses.Address{
|
%Mobilizon.Addresses.Address{
|
||||||
description: sequence("MyAddress"),
|
description: sequence("MyAddress"),
|
||||||
|
|
Loading…
Reference in a new issue