forked from AkkomaGang/akkoma
Merge branch 'cachex-test' into 'develop'
Test framework overhaul (speed, reliability) See merge request pleroma/pleroma!3209
This commit is contained in:
commit
e4f1d8f48c
203 changed files with 659 additions and 430 deletions
1
.gitignore
vendored
1
.gitignore
vendored
|
@ -3,6 +3,7 @@
|
||||||
/db
|
/db
|
||||||
/deps
|
/deps
|
||||||
/*.ez
|
/*.ez
|
||||||
|
/test/instance
|
||||||
/test/uploads
|
/test/uploads
|
||||||
/.elixir_ls
|
/.elixir_ls
|
||||||
/test/fixtures/DSCN0010_tmp.jpg
|
/test/fixtures/DSCN0010_tmp.jpg
|
||||||
|
|
|
@ -47,7 +47,6 @@
|
||||||
config :pleroma, ecto_repos: [Pleroma.Repo]
|
config :pleroma, ecto_repos: [Pleroma.Repo]
|
||||||
|
|
||||||
config :pleroma, Pleroma.Repo,
|
config :pleroma, Pleroma.Repo,
|
||||||
types: Pleroma.PostgresTypes,
|
|
||||||
telemetry_event: [Pleroma.Repo.Instrumenter],
|
telemetry_event: [Pleroma.Repo.Instrumenter],
|
||||||
migration_lock: nil
|
migration_lock: nil
|
||||||
|
|
||||||
|
|
|
@ -47,7 +47,10 @@
|
||||||
password: "postgres",
|
password: "postgres",
|
||||||
database: "pleroma_test",
|
database: "pleroma_test",
|
||||||
hostname: System.get_env("DB_HOST") || "localhost",
|
hostname: System.get_env("DB_HOST") || "localhost",
|
||||||
pool: Ecto.Adapters.SQL.Sandbox
|
pool: Ecto.Adapters.SQL.Sandbox,
|
||||||
|
pool_size: 50
|
||||||
|
|
||||||
|
config :pleroma, :dangerzone, override_repo_pool_size: true
|
||||||
|
|
||||||
# Reduce hash rounds for testing
|
# Reduce hash rounds for testing
|
||||||
config :pbkdf2_elixir, rounds: 1
|
config :pbkdf2_elixir, rounds: 1
|
||||||
|
@ -121,6 +124,16 @@
|
||||||
|
|
||||||
config :pleroma, :mrf, policies: []
|
config :pleroma, :mrf, policies: []
|
||||||
|
|
||||||
|
config :pleroma, :pipeline,
|
||||||
|
object_validator: Pleroma.Web.ActivityPub.ObjectValidatorMock,
|
||||||
|
mrf: Pleroma.Web.ActivityPub.MRFMock,
|
||||||
|
activity_pub: Pleroma.Web.ActivityPub.ActivityPubMock,
|
||||||
|
side_effects: Pleroma.Web.ActivityPub.SideEffectsMock,
|
||||||
|
federator: Pleroma.Web.FederatorMock,
|
||||||
|
config: Pleroma.ConfigMock
|
||||||
|
|
||||||
|
config :pleroma, :cachex, provider: Pleroma.CachexMock
|
||||||
|
|
||||||
if File.exists?("./config/test.secret.exs") do
|
if File.exists?("./config/test.secret.exs") do
|
||||||
import_config "test.secret.exs"
|
import_config "test.secret.exs"
|
||||||
else
|
else
|
||||||
|
|
|
@ -24,6 +24,8 @@ defmodule Pleroma.Activity do
|
||||||
|
|
||||||
@primary_key {:id, FlakeId.Ecto.CompatType, autogenerate: true}
|
@primary_key {:id, FlakeId.Ecto.CompatType, autogenerate: true}
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
schema "activities" do
|
schema "activities" do
|
||||||
field(:data, :map)
|
field(:data, :map)
|
||||||
field(:local, :boolean, default: true)
|
field(:local, :boolean, default: true)
|
||||||
|
@ -298,7 +300,7 @@ def delete_all_by_object_ap_id(_), do: nil
|
||||||
|
|
||||||
defp purge_web_resp_cache(%Activity{} = activity) do
|
defp purge_web_resp_cache(%Activity{} = activity) do
|
||||||
%{path: path} = URI.parse(activity.data["id"])
|
%{path: path} = URI.parse(activity.data["id"])
|
||||||
Cachex.del(:web_resp_cache, path)
|
@cachex.del(:web_resp_cache, path)
|
||||||
activity
|
activity
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
19
lib/pleroma/caching.ex
Normal file
19
lib/pleroma/caching.ex
Normal file
|
@ -0,0 +1,19 @@
|
||||||
|
# Pleroma: A lightweight social networking server
|
||||||
|
# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
|
||||||
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
|
defmodule Pleroma.Caching do
|
||||||
|
@callback get!(Cachex.cache(), any()) :: any()
|
||||||
|
@callback get(Cachex.cache(), any()) :: {atom(), any()}
|
||||||
|
@callback put(Cachex.cache(), any(), any(), Keyword.t()) :: {Cachex.status(), boolean()}
|
||||||
|
@callback put(Cachex.cache(), any(), any()) :: {Cachex.status(), boolean()}
|
||||||
|
@callback fetch!(Cachex.cache(), any(), function() | nil) :: any()
|
||||||
|
# @callback del(Cachex.cache(), any(), Keyword.t()) :: {Cachex.status(), boolean()}
|
||||||
|
@callback del(Cachex.cache(), any()) :: {Cachex.status(), boolean()}
|
||||||
|
@callback stream!(Cachex.cache(), any()) :: Enumerable.t()
|
||||||
|
@callback expire_at(Cachex.cache(), binary(), number()) :: {Cachex.status(), boolean()}
|
||||||
|
@callback exists?(Cachex.cache(), any()) :: {Cachex.status(), boolean()}
|
||||||
|
@callback execute!(Cachex.cache(), function()) :: any()
|
||||||
|
@callback get_and_update(Cachex.cache(), any(), function()) ::
|
||||||
|
{:commit | :ignore, any()}
|
||||||
|
end
|
|
@ -7,6 +7,8 @@ defmodule Pleroma.Captcha do
|
||||||
alias Plug.Crypto.KeyGenerator
|
alias Plug.Crypto.KeyGenerator
|
||||||
alias Plug.Crypto.MessageEncryptor
|
alias Plug.Crypto.MessageEncryptor
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
@doc """
|
@doc """
|
||||||
Ask the configured captcha service for a new captcha
|
Ask the configured captcha service for a new captcha
|
||||||
"""
|
"""
|
||||||
|
@ -86,7 +88,7 @@ defp validate_expiration(created_at) do
|
||||||
end
|
end
|
||||||
|
|
||||||
defp validate_usage(token) do
|
defp validate_usage(token) do
|
||||||
if is_nil(Cachex.get!(:used_captcha_cache, token)) do
|
if is_nil(@cachex.get!(:used_captcha_cache, token)) do
|
||||||
:ok
|
:ok
|
||||||
else
|
else
|
||||||
{:error, :already_used}
|
{:error, :already_used}
|
||||||
|
@ -95,7 +97,7 @@ defp validate_usage(token) do
|
||||||
|
|
||||||
defp mark_captcha_as_used(token) do
|
defp mark_captcha_as_used(token) do
|
||||||
ttl = seconds_valid() |> :timer.seconds()
|
ttl = seconds_valid() |> :timer.seconds()
|
||||||
Cachex.put(:used_captcha_cache, token, true, ttl: ttl)
|
@cachex.put(:used_captcha_cache, token, true, ttl: ttl)
|
||||||
end
|
end
|
||||||
|
|
||||||
defp method, do: Pleroma.Config.get!([__MODULE__, :method])
|
defp method, do: Pleroma.Config.get!([__MODULE__, :method])
|
||||||
|
|
|
@ -3,14 +3,18 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Config do
|
defmodule Pleroma.Config do
|
||||||
|
@behaviour Pleroma.Config.Getting
|
||||||
defmodule Error do
|
defmodule Error do
|
||||||
defexception [:message]
|
defexception [:message]
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
def get(key), do: get(key, nil)
|
def get(key), do: get(key, nil)
|
||||||
|
|
||||||
|
@impl true
|
||||||
def get([key], default), do: get(key, default)
|
def get([key], default), do: get(key, default)
|
||||||
|
|
||||||
|
@impl true
|
||||||
def get([_ | _] = path, default) do
|
def get([_ | _] = path, default) do
|
||||||
case fetch(path) do
|
case fetch(path) do
|
||||||
{:ok, value} -> value
|
{:ok, value} -> value
|
||||||
|
@ -18,6 +22,7 @@ def get([_ | _] = path, default) do
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
def get(key, default) do
|
def get(key, default) do
|
||||||
Application.get_env(:pleroma, key, default)
|
Application.get_env(:pleroma, key, default)
|
||||||
end
|
end
|
||||||
|
|
8
lib/pleroma/config/getting.ex
Normal file
8
lib/pleroma/config/getting.ex
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
# Pleroma: A lightweight social networking server
|
||||||
|
# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
|
||||||
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
|
defmodule Pleroma.Config.Getting do
|
||||||
|
@callback get(any()) :: any()
|
||||||
|
@callback get(any(), any()) :: any()
|
||||||
|
end
|
|
@ -20,6 +20,8 @@ defmodule Pleroma.Emoji.Pack do
|
||||||
name: String.t()
|
name: String.t()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
alias Pleroma.Emoji
|
alias Pleroma.Emoji
|
||||||
alias Pleroma.Emoji.Pack
|
alias Pleroma.Emoji.Pack
|
||||||
alias Pleroma.Utils
|
alias Pleroma.Utils
|
||||||
|
@ -415,7 +417,7 @@ defp create_archive_and_cache(pack, hash) do
|
||||||
ttl_per_file = Pleroma.Config.get!([:emoji, :shared_pack_cache_seconds_per_file])
|
ttl_per_file = Pleroma.Config.get!([:emoji, :shared_pack_cache_seconds_per_file])
|
||||||
overall_ttl = :timer.seconds(ttl_per_file * Enum.count(files))
|
overall_ttl = :timer.seconds(ttl_per_file * Enum.count(files))
|
||||||
|
|
||||||
Cachex.put!(
|
@cachex.put(
|
||||||
:emoji_packs_cache,
|
:emoji_packs_cache,
|
||||||
pack.name,
|
pack.name,
|
||||||
# if pack.json MD5 changes, the cache is not valid anymore
|
# if pack.json MD5 changes, the cache is not valid anymore
|
||||||
|
@ -618,7 +620,7 @@ defp download_archive(url, sha) do
|
||||||
defp fetch_archive(pack) do
|
defp fetch_archive(pack) do
|
||||||
hash = :crypto.hash(:md5, File.read!(pack.pack_file))
|
hash = :crypto.hash(:md5, File.read!(pack.pack_file))
|
||||||
|
|
||||||
case Cachex.get!(:emoji_packs_cache, pack.name) do
|
case @cachex.get!(:emoji_packs_cache, pack.name) do
|
||||||
%{hash: ^hash, pack_data: archive} -> archive
|
%{hash: ^hash, pack_data: archive} -> archive
|
||||||
_ -> create_archive_and_cache(pack, hash)
|
_ -> create_archive_and_cache(pack, hash)
|
||||||
end
|
end
|
||||||
|
|
|
@ -6,6 +6,8 @@ defmodule Pleroma.HTML do
|
||||||
# Scrubbers are compiled on boot so they can be configured in OTP releases
|
# Scrubbers are compiled on boot so they can be configured in OTP releases
|
||||||
# @on_load :compile_scrubbers
|
# @on_load :compile_scrubbers
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
def compile_scrubbers do
|
def compile_scrubbers do
|
||||||
dir = Path.join(:code.priv_dir(:pleroma), "scrubbers")
|
dir = Path.join(:code.priv_dir(:pleroma), "scrubbers")
|
||||||
|
|
||||||
|
@ -56,7 +58,7 @@ def get_cached_scrubbed_html_for_activity(
|
||||||
) do
|
) do
|
||||||
key = "#{key}#{generate_scrubber_signature(scrubbers)}|#{activity.id}"
|
key = "#{key}#{generate_scrubber_signature(scrubbers)}|#{activity.id}"
|
||||||
|
|
||||||
Cachex.fetch!(:scrubber_cache, key, fn _key ->
|
@cachex.fetch!(:scrubber_cache, key, fn _key ->
|
||||||
object = Pleroma.Object.normalize(activity)
|
object = Pleroma.Object.normalize(activity)
|
||||||
ensure_scrubbed_html(content, scrubbers, object.data["fake"] || false, callback)
|
ensure_scrubbed_html(content, scrubbers, object.data["fake"] || false, callback)
|
||||||
end)
|
end)
|
||||||
|
@ -105,7 +107,7 @@ def extract_first_external_url_from_object(%{data: %{"content" => content}} = ob
|
||||||
unless object.data["fake"] do
|
unless object.data["fake"] do
|
||||||
key = "URL|#{object.id}"
|
key = "URL|#{object.id}"
|
||||||
|
|
||||||
Cachex.fetch!(:scrubber_cache, key, fn _key ->
|
@cachex.fetch!(:scrubber_cache, key, fn _key ->
|
||||||
{:commit, {:ok, extract_first_external_url(content)}}
|
{:commit, {:ok, extract_first_external_url(content)}}
|
||||||
end)
|
end)
|
||||||
else
|
else
|
||||||
|
|
|
@ -23,6 +23,8 @@ defmodule Pleroma.Object do
|
||||||
|
|
||||||
@derive {Jason.Encoder, only: [:data]}
|
@derive {Jason.Encoder, only: [:data]}
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
schema "objects" do
|
schema "objects" do
|
||||||
field(:data, :map)
|
field(:data, :map)
|
||||||
|
|
||||||
|
@ -156,9 +158,9 @@ def authorize_access(%Object{}, %User{}), do: :ok
|
||||||
def get_cached_by_ap_id(ap_id) do
|
def get_cached_by_ap_id(ap_id) do
|
||||||
key = "object:#{ap_id}"
|
key = "object:#{ap_id}"
|
||||||
|
|
||||||
with {:ok, nil} <- Cachex.get(:object_cache, key),
|
with {:ok, nil} <- @cachex.get(:object_cache, key),
|
||||||
object when not is_nil(object) <- get_by_ap_id(ap_id),
|
object when not is_nil(object) <- get_by_ap_id(ap_id),
|
||||||
{:ok, true} <- Cachex.put(:object_cache, key, object) do
|
{:ok, true} <- @cachex.put(:object_cache, key, object) do
|
||||||
object
|
object
|
||||||
else
|
else
|
||||||
{:ok, object} -> object
|
{:ok, object} -> object
|
||||||
|
@ -216,13 +218,13 @@ def prune(%Object{data: %{"id" => _id}} = object) do
|
||||||
end
|
end
|
||||||
|
|
||||||
def invalid_object_cache(%Object{data: %{"id" => id}}) do
|
def invalid_object_cache(%Object{data: %{"id" => id}}) do
|
||||||
with {:ok, true} <- Cachex.del(:object_cache, "object:#{id}") do
|
with {:ok, true} <- @cachex.del(:object_cache, "object:#{id}") do
|
||||||
Cachex.del(:web_resp_cache, URI.parse(id).path)
|
@cachex.del(:web_resp_cache, URI.parse(id).path)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def set_cache(%Object{data: %{"id" => ap_id}} = object) do
|
def set_cache(%Object{data: %{"id" => ap_id}} = object) do
|
||||||
Cachex.put(:object_cache, "object:#{ap_id}", object)
|
@cachex.put(:object_cache, "object:#{ap_id}", object)
|
||||||
{:ok, object}
|
{:ok, object}
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -17,6 +17,8 @@ defmodule Pleroma.ReverseProxy do
|
||||||
@failed_request_ttl :timer.seconds(60)
|
@failed_request_ttl :timer.seconds(60)
|
||||||
@methods ~w(GET HEAD)
|
@methods ~w(GET HEAD)
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
def max_read_duration_default, do: @max_read_duration
|
def max_read_duration_default, do: @max_read_duration
|
||||||
def default_cache_control_header, do: @default_cache_control_header
|
def default_cache_control_header, do: @default_cache_control_header
|
||||||
|
|
||||||
|
@ -107,7 +109,7 @@ def call(conn = %{method: method}, url, opts) when method in @methods do
|
||||||
opts
|
opts
|
||||||
end
|
end
|
||||||
|
|
||||||
with {:ok, nil} <- Cachex.get(:failed_proxy_url_cache, url),
|
with {:ok, nil} <- @cachex.get(:failed_proxy_url_cache, url),
|
||||||
{:ok, code, headers, client} <- request(method, url, req_headers, client_opts),
|
{:ok, code, headers, client} <- request(method, url, req_headers, client_opts),
|
||||||
:ok <-
|
:ok <-
|
||||||
header_length_constraint(
|
header_length_constraint(
|
||||||
|
@ -427,6 +429,6 @@ defp track_failed_url(url, error, opts) do
|
||||||
nil
|
nil
|
||||||
end
|
end
|
||||||
|
|
||||||
Cachex.put(:failed_proxy_url_cache, url, true, ttl: ttl)
|
@cachex.put(:failed_proxy_url_cache, url, true, ttl: ttl)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -81,6 +81,8 @@ defmodule Pleroma.User do
|
||||||
]
|
]
|
||||||
]
|
]
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
schema "users" do
|
schema "users" do
|
||||||
field(:bio, :string, default: "")
|
field(:bio, :string, default: "")
|
||||||
field(:raw_bio, :string)
|
field(:raw_bio, :string)
|
||||||
|
@ -246,13 +248,13 @@ def unquote(:"#{outgoing_relation_target}_ap_ids")(user, restrict_deactivated? \
|
||||||
end
|
end
|
||||||
|
|
||||||
def cached_blocked_users_ap_ids(user) do
|
def cached_blocked_users_ap_ids(user) do
|
||||||
Cachex.fetch!(:user_cache, "blocked_users_ap_ids:#{user.ap_id}", fn _ ->
|
@cachex.fetch!(:user_cache, "blocked_users_ap_ids:#{user.ap_id}", fn _ ->
|
||||||
blocked_users_ap_ids(user)
|
blocked_users_ap_ids(user)
|
||||||
end)
|
end)
|
||||||
end
|
end
|
||||||
|
|
||||||
def cached_muted_users_ap_ids(user) do
|
def cached_muted_users_ap_ids(user) do
|
||||||
Cachex.fetch!(:user_cache, "muted_users_ap_ids:#{user.ap_id}", fn _ ->
|
@cachex.fetch!(:user_cache, "muted_users_ap_ids:#{user.ap_id}", fn _ ->
|
||||||
muted_users_ap_ids(user)
|
muted_users_ap_ids(user)
|
||||||
end)
|
end)
|
||||||
end
|
end
|
||||||
|
@ -1048,9 +1050,9 @@ def set_cache({:ok, user}), do: set_cache(user)
|
||||||
def set_cache({:error, err}), do: {:error, err}
|
def set_cache({:error, err}), do: {:error, err}
|
||||||
|
|
||||||
def set_cache(%User{} = user) do
|
def set_cache(%User{} = user) do
|
||||||
Cachex.put(:user_cache, "ap_id:#{user.ap_id}", user)
|
@cachex.put(:user_cache, "ap_id:#{user.ap_id}", user)
|
||||||
Cachex.put(:user_cache, "nickname:#{user.nickname}", user)
|
@cachex.put(:user_cache, "nickname:#{user.nickname}", user)
|
||||||
Cachex.put(:user_cache, "friends_ap_ids:#{user.nickname}", get_user_friends_ap_ids(user))
|
@cachex.put(:user_cache, "friends_ap_ids:#{user.nickname}", get_user_friends_ap_ids(user))
|
||||||
{:ok, user}
|
{:ok, user}
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -1073,26 +1075,26 @@ def get_user_friends_ap_ids(user) do
|
||||||
|
|
||||||
@spec get_cached_user_friends_ap_ids(User.t()) :: [String.t()]
|
@spec get_cached_user_friends_ap_ids(User.t()) :: [String.t()]
|
||||||
def get_cached_user_friends_ap_ids(user) do
|
def get_cached_user_friends_ap_ids(user) do
|
||||||
Cachex.fetch!(:user_cache, "friends_ap_ids:#{user.ap_id}", fn _ ->
|
@cachex.fetch!(:user_cache, "friends_ap_ids:#{user.ap_id}", fn _ ->
|
||||||
get_user_friends_ap_ids(user)
|
get_user_friends_ap_ids(user)
|
||||||
end)
|
end)
|
||||||
end
|
end
|
||||||
|
|
||||||
def invalidate_cache(user) do
|
def invalidate_cache(user) do
|
||||||
Cachex.del(:user_cache, "ap_id:#{user.ap_id}")
|
@cachex.del(:user_cache, "ap_id:#{user.ap_id}")
|
||||||
Cachex.del(:user_cache, "nickname:#{user.nickname}")
|
@cachex.del(:user_cache, "nickname:#{user.nickname}")
|
||||||
Cachex.del(:user_cache, "friends_ap_ids:#{user.ap_id}")
|
@cachex.del(:user_cache, "friends_ap_ids:#{user.ap_id}")
|
||||||
Cachex.del(:user_cache, "blocked_users_ap_ids:#{user.ap_id}")
|
@cachex.del(:user_cache, "blocked_users_ap_ids:#{user.ap_id}")
|
||||||
Cachex.del(:user_cache, "muted_users_ap_ids:#{user.ap_id}")
|
@cachex.del(:user_cache, "muted_users_ap_ids:#{user.ap_id}")
|
||||||
end
|
end
|
||||||
|
|
||||||
@spec get_cached_by_ap_id(String.t()) :: User.t() | nil
|
@spec get_cached_by_ap_id(String.t()) :: User.t() | nil
|
||||||
def get_cached_by_ap_id(ap_id) do
|
def get_cached_by_ap_id(ap_id) do
|
||||||
key = "ap_id:#{ap_id}"
|
key = "ap_id:#{ap_id}"
|
||||||
|
|
||||||
with {:ok, nil} <- Cachex.get(:user_cache, key),
|
with {:ok, nil} <- @cachex.get(:user_cache, key),
|
||||||
user when not is_nil(user) <- get_by_ap_id(ap_id),
|
user when not is_nil(user) <- get_by_ap_id(ap_id),
|
||||||
{:ok, true} <- Cachex.put(:user_cache, key, user) do
|
{:ok, true} <- @cachex.put(:user_cache, key, user) do
|
||||||
user
|
user
|
||||||
else
|
else
|
||||||
{:ok, user} -> user
|
{:ok, user} -> user
|
||||||
|
@ -1104,11 +1106,11 @@ def get_cached_by_id(id) do
|
||||||
key = "id:#{id}"
|
key = "id:#{id}"
|
||||||
|
|
||||||
ap_id =
|
ap_id =
|
||||||
Cachex.fetch!(:user_cache, key, fn _ ->
|
@cachex.fetch!(:user_cache, key, fn _ ->
|
||||||
user = get_by_id(id)
|
user = get_by_id(id)
|
||||||
|
|
||||||
if user do
|
if user do
|
||||||
Cachex.put(:user_cache, "ap_id:#{user.ap_id}", user)
|
@cachex.put(:user_cache, "ap_id:#{user.ap_id}", user)
|
||||||
{:commit, user.ap_id}
|
{:commit, user.ap_id}
|
||||||
else
|
else
|
||||||
{:ignore, ""}
|
{:ignore, ""}
|
||||||
|
@ -1121,7 +1123,7 @@ def get_cached_by_id(id) do
|
||||||
def get_cached_by_nickname(nickname) do
|
def get_cached_by_nickname(nickname) do
|
||||||
key = "nickname:#{nickname}"
|
key = "nickname:#{nickname}"
|
||||||
|
|
||||||
Cachex.fetch!(:user_cache, key, fn ->
|
@cachex.fetch!(:user_cache, key, fn _ ->
|
||||||
case get_or_fetch_by_nickname(nickname) do
|
case get_or_fetch_by_nickname(nickname) do
|
||||||
{:ok, user} -> {:commit, user}
|
{:ok, user} -> {:commit, user}
|
||||||
{:error, _error} -> {:ignore, nil}
|
{:error, _error} -> {:ignore, nil}
|
||||||
|
@ -1390,7 +1392,7 @@ def mute(%User{} = muter, %User{} = mutee, params \\ %{}) do
|
||||||
)
|
)
|
||||||
end
|
end
|
||||||
|
|
||||||
Cachex.del(:user_cache, "muted_users_ap_ids:#{muter.ap_id}")
|
@cachex.del(:user_cache, "muted_users_ap_ids:#{muter.ap_id}")
|
||||||
|
|
||||||
{:ok, Enum.filter([user_mute, user_notification_mute], & &1)}
|
{:ok, Enum.filter([user_mute, user_notification_mute], & &1)}
|
||||||
end
|
end
|
||||||
|
@ -1400,7 +1402,7 @@ def unmute(%User{} = muter, %User{} = mutee) do
|
||||||
with {:ok, user_mute} <- UserRelationship.delete_mute(muter, mutee),
|
with {:ok, user_mute} <- UserRelationship.delete_mute(muter, mutee),
|
||||||
{:ok, user_notification_mute} <-
|
{:ok, user_notification_mute} <-
|
||||||
UserRelationship.delete_notification_mute(muter, mutee) do
|
UserRelationship.delete_notification_mute(muter, mutee) do
|
||||||
Cachex.del(:user_cache, "muted_users_ap_ids:#{muter.ap_id}")
|
@cachex.del(:user_cache, "muted_users_ap_ids:#{muter.ap_id}")
|
||||||
{:ok, [user_mute, user_notification_mute]}
|
{:ok, [user_mute, user_notification_mute]}
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -2408,7 +2410,7 @@ def unblock_domain(user, domain_blocked) do
|
||||||
{:ok, UserRelationship.t()} | {:error, Ecto.Changeset.t()}
|
{:ok, UserRelationship.t()} | {:error, Ecto.Changeset.t()}
|
||||||
defp add_to_block(%User{} = user, %User{} = blocked) do
|
defp add_to_block(%User{} = user, %User{} = blocked) do
|
||||||
with {:ok, relationship} <- UserRelationship.create_block(user, blocked) do
|
with {:ok, relationship} <- UserRelationship.create_block(user, blocked) do
|
||||||
Cachex.del(:user_cache, "blocked_users_ap_ids:#{user.ap_id}")
|
@cachex.del(:user_cache, "blocked_users_ap_ids:#{user.ap_id}")
|
||||||
{:ok, relationship}
|
{:ok, relationship}
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -2417,7 +2419,7 @@ defp add_to_block(%User{} = user, %User{} = blocked) do
|
||||||
{:ok, UserRelationship.t()} | {:ok, nil} | {:error, Ecto.Changeset.t()}
|
{:ok, UserRelationship.t()} | {:ok, nil} | {:error, Ecto.Changeset.t()}
|
||||||
defp remove_from_block(%User{} = user, %User{} = blocked) do
|
defp remove_from_block(%User{} = user, %User{} = blocked) do
|
||||||
with {:ok, relationship} <- UserRelationship.delete_block(user, blocked) do
|
with {:ok, relationship} <- UserRelationship.delete_block(user, blocked) do
|
||||||
Cachex.del(:user_cache, "blocked_users_ap_ids:#{user.ap_id}")
|
@cachex.del(:user_cache, "blocked_users_ap_ids:#{user.ap_id}")
|
||||||
{:ok, relationship}
|
{:ok, relationship}
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -32,6 +32,8 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do
|
||||||
require Logger
|
require Logger
|
||||||
require Pleroma.Constants
|
require Pleroma.Constants
|
||||||
|
|
||||||
|
@behaviour Pleroma.Web.ActivityPub.ActivityPub.Persisting
|
||||||
|
|
||||||
defp get_recipients(%{"type" => "Create"} = data) do
|
defp get_recipients(%{"type" => "Create"} = data) do
|
||||||
to = Map.get(data, "to", [])
|
to = Map.get(data, "to", [])
|
||||||
cc = Map.get(data, "cc", [])
|
cc = Map.get(data, "cc", [])
|
||||||
|
@ -85,13 +87,14 @@ defp increase_replies_count_if_reply(%{
|
||||||
defp increase_replies_count_if_reply(_create_data), do: :noop
|
defp increase_replies_count_if_reply(_create_data), do: :noop
|
||||||
|
|
||||||
@object_types ~w[ChatMessage Question Answer Audio Video Event Article]
|
@object_types ~w[ChatMessage Question Answer Audio Video Event Article]
|
||||||
@spec persist(map(), keyword()) :: {:ok, Activity.t() | Object.t()}
|
@impl true
|
||||||
def persist(%{"type" => type} = object, meta) when type in @object_types do
|
def persist(%{"type" => type} = object, meta) when type in @object_types do
|
||||||
with {:ok, object} <- Object.create(object) do
|
with {:ok, object} <- Object.create(object) do
|
||||||
{:ok, object, meta}
|
{:ok, object, meta}
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
def persist(object, meta) do
|
def persist(object, meta) do
|
||||||
with local <- Keyword.fetch!(meta, :local),
|
with local <- Keyword.fetch!(meta, :local),
|
||||||
{recipients, _, _} <- get_recipients(object),
|
{recipients, _, _} <- get_recipients(object),
|
||||||
|
|
7
lib/pleroma/web/activity_pub/activity_pub/persisting.ex
Normal file
7
lib/pleroma/web/activity_pub/activity_pub/persisting.ex
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
# Pleroma: A lightweight social networking server
|
||||||
|
# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
|
||||||
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
|
defmodule Pleroma.Web.ActivityPub.ActivityPub.Persisting do
|
||||||
|
@callback persist(map(), keyword()) :: {:ok, Activity.t() | Object.t()}
|
||||||
|
end
|
|
@ -5,6 +5,8 @@
|
||||||
defmodule Pleroma.Web.ActivityPub.MRF do
|
defmodule Pleroma.Web.ActivityPub.MRF do
|
||||||
require Logger
|
require Logger
|
||||||
|
|
||||||
|
@behaviour Pleroma.Web.ActivityPub.MRF.PipelineFiltering
|
||||||
|
|
||||||
@mrf_config_descriptions [
|
@mrf_config_descriptions [
|
||||||
%{
|
%{
|
||||||
group: :pleroma,
|
group: :pleroma,
|
||||||
|
@ -70,6 +72,7 @@ def filter(policies, %{} = message) do
|
||||||
|
|
||||||
def filter(%{} = object), do: get_policies() |> filter(object)
|
def filter(%{} = object), do: get_policies() |> filter(object)
|
||||||
|
|
||||||
|
@impl true
|
||||||
def pipeline_filter(%{} = message, meta) do
|
def pipeline_filter(%{} = message, meta) do
|
||||||
object = meta[:object_data]
|
object = meta[:object_data]
|
||||||
ap_id = message["object"]
|
ap_id = message["object"]
|
||||||
|
|
7
lib/pleroma/web/activity_pub/mrf/pipeline_filtering.ex
Normal file
7
lib/pleroma/web/activity_pub/mrf/pipeline_filtering.ex
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
# Pleroma: A lightweight social networking server
|
||||||
|
# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
|
||||||
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
|
defmodule Pleroma.Web.ActivityPub.MRF.PipelineFiltering do
|
||||||
|
@callback pipeline_filter(map(), keyword()) :: {:ok, map(), keyword()} | {:error, any()}
|
||||||
|
end
|
|
@ -9,6 +9,8 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidator do
|
||||||
the system.
|
the system.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
@behaviour Pleroma.Web.ActivityPub.ObjectValidator.Validating
|
||||||
|
|
||||||
alias Pleroma.Activity
|
alias Pleroma.Activity
|
||||||
alias Pleroma.EctoType.ActivityPub.ObjectValidators
|
alias Pleroma.EctoType.ActivityPub.ObjectValidators
|
||||||
alias Pleroma.Object
|
alias Pleroma.Object
|
||||||
|
@ -32,7 +34,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidator do
|
||||||
alias Pleroma.Web.ActivityPub.ObjectValidators.UndoValidator
|
alias Pleroma.Web.ActivityPub.ObjectValidators.UndoValidator
|
||||||
alias Pleroma.Web.ActivityPub.ObjectValidators.UpdateValidator
|
alias Pleroma.Web.ActivityPub.ObjectValidators.UpdateValidator
|
||||||
|
|
||||||
@spec validate(map(), keyword()) :: {:ok, map(), keyword()} | {:error, any()}
|
@impl true
|
||||||
def validate(object, meta)
|
def validate(object, meta)
|
||||||
|
|
||||||
def validate(%{"type" => type} = object, meta)
|
def validate(%{"type" => type} = object, meta)
|
||||||
|
|
|
@ -0,0 +1,7 @@
|
||||||
|
# Pleroma: A lightweight social networking server
|
||||||
|
# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
|
||||||
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
|
defmodule Pleroma.Web.ActivityPub.ObjectValidator.Validating do
|
||||||
|
@callback validate(map(), keyword()) :: {:ok, map(), keyword()} | {:error, any()}
|
||||||
|
end
|
|
@ -14,12 +14,19 @@ defmodule Pleroma.Web.ActivityPub.Pipeline do
|
||||||
alias Pleroma.Web.ActivityPub.Visibility
|
alias Pleroma.Web.ActivityPub.Visibility
|
||||||
alias Pleroma.Web.Federator
|
alias Pleroma.Web.Federator
|
||||||
|
|
||||||
|
@side_effects Config.get([:pipeline, :side_effects], SideEffects)
|
||||||
|
@federator Config.get([:pipeline, :federator], Federator)
|
||||||
|
@object_validator Config.get([:pipeline, :object_validator], ObjectValidator)
|
||||||
|
@mrf Config.get([:pipeline, :mrf], MRF)
|
||||||
|
@activity_pub Config.get([:pipeline, :activity_pub], ActivityPub)
|
||||||
|
@config Config.get([:pipeline, :config], Config)
|
||||||
|
|
||||||
@spec common_pipeline(map(), keyword()) ::
|
@spec common_pipeline(map(), keyword()) ::
|
||||||
{:ok, Activity.t() | Object.t(), keyword()} | {:error, any()}
|
{:ok, Activity.t() | Object.t(), keyword()} | {:error, any()}
|
||||||
def common_pipeline(object, meta) do
|
def common_pipeline(object, meta) do
|
||||||
case Repo.transaction(fn -> do_common_pipeline(object, meta) end) do
|
case Repo.transaction(fn -> do_common_pipeline(object, meta) end) do
|
||||||
{:ok, {:ok, activity, meta}} ->
|
{:ok, {:ok, activity, meta}} ->
|
||||||
SideEffects.handle_after_transaction(meta)
|
@side_effects.handle_after_transaction(meta)
|
||||||
{:ok, activity, meta}
|
{:ok, activity, meta}
|
||||||
|
|
||||||
{:ok, value} ->
|
{:ok, value} ->
|
||||||
|
@ -35,13 +42,13 @@ def common_pipeline(object, meta) do
|
||||||
|
|
||||||
def do_common_pipeline(object, meta) do
|
def do_common_pipeline(object, meta) do
|
||||||
with {_, {:ok, validated_object, meta}} <-
|
with {_, {:ok, validated_object, meta}} <-
|
||||||
{:validate_object, ObjectValidator.validate(object, meta)},
|
{:validate_object, @object_validator.validate(object, meta)},
|
||||||
{_, {:ok, mrfd_object, meta}} <-
|
{_, {:ok, mrfd_object, meta}} <-
|
||||||
{:mrf_object, MRF.pipeline_filter(validated_object, meta)},
|
{:mrf_object, @mrf.pipeline_filter(validated_object, meta)},
|
||||||
{_, {:ok, activity, meta}} <-
|
{_, {:ok, activity, meta}} <-
|
||||||
{:persist_object, ActivityPub.persist(mrfd_object, meta)},
|
{:persist_object, @activity_pub.persist(mrfd_object, meta)},
|
||||||
{_, {:ok, activity, meta}} <-
|
{_, {:ok, activity, meta}} <-
|
||||||
{:execute_side_effects, SideEffects.handle(activity, meta)},
|
{:execute_side_effects, @side_effects.handle(activity, meta)},
|
||||||
{_, {:ok, _}} <- {:federation, maybe_federate(activity, meta)} do
|
{_, {:ok, _}} <- {:federation, maybe_federate(activity, meta)} do
|
||||||
{:ok, activity, meta}
|
{:ok, activity, meta}
|
||||||
else
|
else
|
||||||
|
@ -54,7 +61,7 @@ defp maybe_federate(%Object{}, _), do: {:ok, :not_federated}
|
||||||
|
|
||||||
defp maybe_federate(%Activity{} = activity, meta) do
|
defp maybe_federate(%Activity{} = activity, meta) do
|
||||||
with {:ok, local} <- Keyword.fetch(meta, :local) do
|
with {:ok, local} <- Keyword.fetch(meta, :local) do
|
||||||
do_not_federate = meta[:do_not_federate] || !Config.get([:instance, :federating])
|
do_not_federate = meta[:do_not_federate] || !@config.get([:instance, :federating])
|
||||||
|
|
||||||
if !do_not_federate and local and not Visibility.is_local_public?(activity) do
|
if !do_not_federate and local and not Visibility.is_local_public?(activity) do
|
||||||
activity =
|
activity =
|
||||||
|
@ -64,7 +71,7 @@ defp maybe_federate(%Activity{} = activity, meta) do
|
||||||
activity
|
activity
|
||||||
end
|
end
|
||||||
|
|
||||||
Federator.publish(activity)
|
@federator.publish(activity)
|
||||||
{:ok, :federated}
|
{:ok, :federated}
|
||||||
else
|
else
|
||||||
{:ok, :not_federated}
|
{:ok, :not_federated}
|
||||||
|
|
|
@ -27,11 +27,17 @@ defmodule Pleroma.Web.ActivityPub.SideEffects do
|
||||||
|
|
||||||
require Logger
|
require Logger
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
|
@behaviour Pleroma.Web.ActivityPub.SideEffects.Handling
|
||||||
|
|
||||||
|
@impl true
|
||||||
def handle(object, meta \\ [])
|
def handle(object, meta \\ [])
|
||||||
|
|
||||||
# Task this handles
|
# Task this handles
|
||||||
# - Follows
|
# - Follows
|
||||||
# - Sends a notification
|
# - Sends a notification
|
||||||
|
@impl true
|
||||||
def handle(
|
def handle(
|
||||||
%{
|
%{
|
||||||
data: %{
|
data: %{
|
||||||
|
@ -59,6 +65,7 @@ def handle(
|
||||||
# - Rejects all existing follow activities for this person
|
# - Rejects all existing follow activities for this person
|
||||||
# - Updates the follow state
|
# - Updates the follow state
|
||||||
# - Dismisses notification
|
# - Dismisses notification
|
||||||
|
@impl true
|
||||||
def handle(
|
def handle(
|
||||||
%{
|
%{
|
||||||
data: %{
|
data: %{
|
||||||
|
@ -85,6 +92,7 @@ def handle(
|
||||||
# - Follows if possible
|
# - Follows if possible
|
||||||
# - Sends a notification
|
# - Sends a notification
|
||||||
# - Generates accept or reject if appropriate
|
# - Generates accept or reject if appropriate
|
||||||
|
@impl true
|
||||||
def handle(
|
def handle(
|
||||||
%{
|
%{
|
||||||
data: %{
|
data: %{
|
||||||
|
@ -126,6 +134,7 @@ def handle(
|
||||||
|
|
||||||
# Tasks this handles:
|
# Tasks this handles:
|
||||||
# - Unfollow and block
|
# - Unfollow and block
|
||||||
|
@impl true
|
||||||
def handle(
|
def handle(
|
||||||
%{data: %{"type" => "Block", "object" => blocked_user, "actor" => blocking_user}} =
|
%{data: %{"type" => "Block", "object" => blocked_user, "actor" => blocking_user}} =
|
||||||
object,
|
object,
|
||||||
|
@ -144,6 +153,7 @@ def handle(
|
||||||
#
|
#
|
||||||
# For a local user, we also get a changeset with the full information, so we
|
# For a local user, we also get a changeset with the full information, so we
|
||||||
# can update non-federating, non-activitypub settings as well.
|
# can update non-federating, non-activitypub settings as well.
|
||||||
|
@impl true
|
||||||
def handle(%{data: %{"type" => "Update", "object" => updated_object}} = object, meta) do
|
def handle(%{data: %{"type" => "Update", "object" => updated_object}} = object, meta) do
|
||||||
if changeset = Keyword.get(meta, :user_update_changeset) do
|
if changeset = Keyword.get(meta, :user_update_changeset) do
|
||||||
changeset
|
changeset
|
||||||
|
@ -162,6 +172,7 @@ def handle(%{data: %{"type" => "Update", "object" => updated_object}} = object,
|
||||||
# Tasks this handles:
|
# Tasks this handles:
|
||||||
# - Add like to object
|
# - Add like to object
|
||||||
# - Set up notification
|
# - Set up notification
|
||||||
|
@impl true
|
||||||
def handle(%{data: %{"type" => "Like"}} = object, meta) do
|
def handle(%{data: %{"type" => "Like"}} = object, meta) do
|
||||||
liked_object = Object.get_by_ap_id(object.data["object"])
|
liked_object = Object.get_by_ap_id(object.data["object"])
|
||||||
Utils.add_like_to_object(object, liked_object)
|
Utils.add_like_to_object(object, liked_object)
|
||||||
|
@ -179,6 +190,7 @@ def handle(%{data: %{"type" => "Like"}} = object, meta) do
|
||||||
# - Increase replies count
|
# - Increase replies count
|
||||||
# - Set up ActivityExpiration
|
# - Set up ActivityExpiration
|
||||||
# - Set up notifications
|
# - Set up notifications
|
||||||
|
@impl true
|
||||||
def handle(%{data: %{"type" => "Create"}} = activity, meta) do
|
def handle(%{data: %{"type" => "Create"}} = activity, meta) do
|
||||||
with {:ok, object, meta} <- handle_object_creation(meta[:object_data], meta),
|
with {:ok, object, meta} <- handle_object_creation(meta[:object_data], meta),
|
||||||
%User{} = user <- User.get_cached_by_ap_id(activity.data["actor"]) do
|
%User{} = user <- User.get_cached_by_ap_id(activity.data["actor"]) do
|
||||||
|
@ -207,6 +219,7 @@ def handle(%{data: %{"type" => "Create"}} = activity, meta) do
|
||||||
# - Add announce to object
|
# - Add announce to object
|
||||||
# - Set up notification
|
# - Set up notification
|
||||||
# - Stream out the announce
|
# - Stream out the announce
|
||||||
|
@impl true
|
||||||
def handle(%{data: %{"type" => "Announce"}} = object, meta) do
|
def handle(%{data: %{"type" => "Announce"}} = object, meta) do
|
||||||
announced_object = Object.get_by_ap_id(object.data["object"])
|
announced_object = Object.get_by_ap_id(object.data["object"])
|
||||||
user = User.get_cached_by_ap_id(object.data["actor"])
|
user = User.get_cached_by_ap_id(object.data["actor"])
|
||||||
|
@ -224,6 +237,7 @@ def handle(%{data: %{"type" => "Announce"}} = object, meta) do
|
||||||
{:ok, object, meta}
|
{:ok, object, meta}
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
def handle(%{data: %{"type" => "Undo", "object" => undone_object}} = object, meta) do
|
def handle(%{data: %{"type" => "Undo", "object" => undone_object}} = object, meta) do
|
||||||
with undone_object <- Activity.get_by_ap_id(undone_object),
|
with undone_object <- Activity.get_by_ap_id(undone_object),
|
||||||
:ok <- handle_undoing(undone_object) do
|
:ok <- handle_undoing(undone_object) do
|
||||||
|
@ -234,6 +248,7 @@ def handle(%{data: %{"type" => "Undo", "object" => undone_object}} = object, met
|
||||||
# Tasks this handles:
|
# Tasks this handles:
|
||||||
# - Add reaction to object
|
# - Add reaction to object
|
||||||
# - Set up notification
|
# - Set up notification
|
||||||
|
@impl true
|
||||||
def handle(%{data: %{"type" => "EmojiReact"}} = object, meta) do
|
def handle(%{data: %{"type" => "EmojiReact"}} = object, meta) do
|
||||||
reacted_object = Object.get_by_ap_id(object.data["object"])
|
reacted_object = Object.get_by_ap_id(object.data["object"])
|
||||||
Utils.add_emoji_reaction_to_object(object, reacted_object)
|
Utils.add_emoji_reaction_to_object(object, reacted_object)
|
||||||
|
@ -250,6 +265,7 @@ def handle(%{data: %{"type" => "EmojiReact"}} = object, meta) do
|
||||||
# - Reduce the user note count
|
# - Reduce the user note count
|
||||||
# - Reduce the reply count
|
# - Reduce the reply count
|
||||||
# - Stream out the activity
|
# - Stream out the activity
|
||||||
|
@impl true
|
||||||
def handle(%{data: %{"type" => "Delete", "object" => deleted_object}} = object, meta) do
|
def handle(%{data: %{"type" => "Delete", "object" => deleted_object}} = object, meta) do
|
||||||
deleted_object =
|
deleted_object =
|
||||||
Object.normalize(deleted_object, false) ||
|
Object.normalize(deleted_object, false) ||
|
||||||
|
@ -295,6 +311,7 @@ def handle(%{data: %{"type" => "Delete", "object" => deleted_object}} = object,
|
||||||
end
|
end
|
||||||
|
|
||||||
# Nothing to do
|
# Nothing to do
|
||||||
|
@impl true
|
||||||
def handle(object, meta) do
|
def handle(object, meta) do
|
||||||
{:ok, object, meta}
|
{:ok, object, meta}
|
||||||
end
|
end
|
||||||
|
@ -312,7 +329,7 @@ def handle_object_creation(%{"type" => "ChatMessage"} = object, meta) do
|
||||||
{:ok, chat} = Chat.bump_or_create(user.id, other_user.ap_id)
|
{:ok, chat} = Chat.bump_or_create(user.id, other_user.ap_id)
|
||||||
{:ok, cm_ref} = MessageReference.create(chat, object, user.ap_id != actor.ap_id)
|
{:ok, cm_ref} = MessageReference.create(chat, object, user.ap_id != actor.ap_id)
|
||||||
|
|
||||||
Cachex.put(
|
@cachex.put(
|
||||||
:chat_message_id_idempotency_key_cache,
|
:chat_message_id_idempotency_key_cache,
|
||||||
cm_ref.id,
|
cm_ref.id,
|
||||||
meta[:idempotency_key]
|
meta[:idempotency_key]
|
||||||
|
@ -439,6 +456,7 @@ defp add_notifications(meta, notifications) do
|
||||||
|> Keyword.put(:notifications, notifications ++ existing)
|
|> Keyword.put(:notifications, notifications ++ existing)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
def handle_after_transaction(meta) do
|
def handle_after_transaction(meta) do
|
||||||
meta
|
meta
|
||||||
|> send_notifications()
|
|> send_notifications()
|
||||||
|
|
8
lib/pleroma/web/activity_pub/side_effects/handling.ex
Normal file
8
lib/pleroma/web/activity_pub/side_effects/handling.ex
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
# Pleroma: A lightweight social networking server
|
||||||
|
# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
|
||||||
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
|
defmodule Pleroma.Web.ActivityPub.SideEffects.Handling do
|
||||||
|
@callback handle(map(), keyword()) :: {:ok, map(), keyword()} | {:error, any()}
|
||||||
|
@callback handle_after_transaction(map()) :: map()
|
||||||
|
end
|
|
@ -9,6 +9,8 @@ defmodule Pleroma.Web.AdminAPI.MediaProxyCacheController do
|
||||||
alias Pleroma.Web.MediaProxy
|
alias Pleroma.Web.MediaProxy
|
||||||
alias Pleroma.Web.Plugs.OAuthScopesPlug
|
alias Pleroma.Web.Plugs.OAuthScopesPlug
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
plug(Pleroma.Web.ApiSpec.CastAndValidate)
|
plug(Pleroma.Web.ApiSpec.CastAndValidate)
|
||||||
|
|
||||||
plug(
|
plug(
|
||||||
|
@ -38,7 +40,7 @@ def index(%{assigns: %{user: _}} = conn, params) do
|
||||||
|
|
||||||
defp fetch_entries(params) do
|
defp fetch_entries(params) do
|
||||||
MediaProxy.cache_table()
|
MediaProxy.cache_table()
|
||||||
|> Cachex.stream!(Cachex.Query.create(true, :key))
|
|> @cachex.stream!(Cachex.Query.create(true, :key))
|
||||||
|> filter_entries(params[:query])
|
|> filter_entries(params[:query])
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -15,6 +15,8 @@ defmodule Pleroma.Web.Federator do
|
||||||
|
|
||||||
require Logger
|
require Logger
|
||||||
|
|
||||||
|
@behaviour Pleroma.Web.Federator.Publishing
|
||||||
|
|
||||||
@doc """
|
@doc """
|
||||||
Returns `true` if the distance to target object does not exceed max configured value.
|
Returns `true` if the distance to target object does not exceed max configured value.
|
||||||
Serves to prevent fetching of very long threads, especially useful on smaller instances.
|
Serves to prevent fetching of very long threads, especially useful on smaller instances.
|
||||||
|
@ -39,10 +41,12 @@ def incoming_ap_doc(params) do
|
||||||
ReceiverWorker.enqueue("incoming_ap_doc", %{"params" => params})
|
ReceiverWorker.enqueue("incoming_ap_doc", %{"params" => params})
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
def publish(%{id: "pleroma:fakeid"} = activity) do
|
def publish(%{id: "pleroma:fakeid"} = activity) do
|
||||||
perform(:publish, activity)
|
perform(:publish, activity)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
def publish(activity) do
|
def publish(activity) do
|
||||||
PublisherWorker.enqueue("publish", %{"activity_id" => activity.id})
|
PublisherWorker.enqueue("publish", %{"activity_id" => activity.id})
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,8 +2,6 @@
|
||||||
# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
|
# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
Postgrex.Types.define(
|
defmodule Pleroma.Web.Federator.Publishing do
|
||||||
Pleroma.PostgresTypes,
|
@callback publish(map()) :: any()
|
||||||
[] ++ Ecto.Adapters.Postgres.extensions(),
|
end
|
||||||
json: Jason
|
|
||||||
)
|
|
|
@ -26,6 +26,8 @@ defmodule Pleroma.Web.MastodonAPI.PollController do
|
||||||
|
|
||||||
defdelegate open_api_operation(action), to: Pleroma.Web.ApiSpec.PollOperation
|
defdelegate open_api_operation(action), to: Pleroma.Web.ApiSpec.PollOperation
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
@doc "GET /api/v1/polls/:id"
|
@doc "GET /api/v1/polls/:id"
|
||||||
def show(%{assigns: %{user: user}} = conn, %{id: id}) do
|
def show(%{assigns: %{user: user}} = conn, %{id: id}) do
|
||||||
with %Object{} = object <- Object.get_by_id_and_maybe_refetch(id, interval: 60),
|
with %Object{} = object <- Object.get_by_id_and_maybe_refetch(id, interval: 60),
|
||||||
|
@ -55,7 +57,7 @@ def vote(%{assigns: %{user: user}, body_params: %{choices: choices}} = conn, %{i
|
||||||
defp get_cached_vote_or_vote(user, object, choices) do
|
defp get_cached_vote_or_vote(user, object, choices) do
|
||||||
idempotency_key = "polls:#{user.id}:#{object.data["id"]}"
|
idempotency_key = "polls:#{user.id}:#{object.data["id"]}"
|
||||||
|
|
||||||
Cachex.fetch!(:idempotency_cache, idempotency_key, fn ->
|
@cachex.fetch!(:idempotency_cache, idempotency_key, fn _ ->
|
||||||
case CommonAPI.vote(user, object, choices) do
|
case CommonAPI.vote(user, object, choices) do
|
||||||
{:error, _message} = res -> {:ignore, res}
|
{:error, _message} = res -> {:ignore, res}
|
||||||
res -> {:commit, res}
|
res -> {:commit, res}
|
||||||
|
|
|
@ -12,29 +12,31 @@ defmodule Pleroma.Web.MediaProxy do
|
||||||
@base64_opts [padding: false]
|
@base64_opts [padding: false]
|
||||||
@cache_table :banned_urls_cache
|
@cache_table :banned_urls_cache
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
def cache_table, do: @cache_table
|
def cache_table, do: @cache_table
|
||||||
|
|
||||||
@spec in_banned_urls(String.t()) :: boolean()
|
@spec in_banned_urls(String.t()) :: boolean()
|
||||||
def in_banned_urls(url), do: elem(Cachex.exists?(@cache_table, url(url)), 1)
|
def in_banned_urls(url), do: elem(@cachex.exists?(@cache_table, url(url)), 1)
|
||||||
|
|
||||||
def remove_from_banned_urls(urls) when is_list(urls) do
|
def remove_from_banned_urls(urls) when is_list(urls) do
|
||||||
Cachex.execute!(@cache_table, fn cache ->
|
@cachex.execute!(@cache_table, fn cache ->
|
||||||
Enum.each(Invalidation.prepare_urls(urls), &Cachex.del(cache, &1))
|
Enum.each(Invalidation.prepare_urls(urls), &@cachex.del(cache, &1))
|
||||||
end)
|
end)
|
||||||
end
|
end
|
||||||
|
|
||||||
def remove_from_banned_urls(url) when is_binary(url) do
|
def remove_from_banned_urls(url) when is_binary(url) do
|
||||||
Cachex.del(@cache_table, url(url))
|
@cachex.del(@cache_table, url(url))
|
||||||
end
|
end
|
||||||
|
|
||||||
def put_in_banned_urls(urls) when is_list(urls) do
|
def put_in_banned_urls(urls) when is_list(urls) do
|
||||||
Cachex.execute!(@cache_table, fn cache ->
|
@cachex.execute!(@cache_table, fn cache ->
|
||||||
Enum.each(Invalidation.prepare_urls(urls), &Cachex.put(cache, &1, true))
|
Enum.each(Invalidation.prepare_urls(urls), &@cachex.put(cache, &1, true))
|
||||||
end)
|
end)
|
||||||
end
|
end
|
||||||
|
|
||||||
def put_in_banned_urls(url) when is_binary(url) do
|
def put_in_banned_urls(url) when is_binary(url) do
|
||||||
Cachex.put(@cache_table, url(url), true)
|
@cachex.put(@cache_table, url(url), true)
|
||||||
end
|
end
|
||||||
|
|
||||||
def url(url) when is_nil(url) or url == "", do: nil
|
def url(url) when is_nil(url) or url == "", do: nil
|
||||||
|
|
|
@ -10,6 +10,8 @@ defmodule Pleroma.Web.PleromaAPI.Chat.MessageReferenceView do
|
||||||
alias Pleroma.Web.CommonAPI.Utils
|
alias Pleroma.Web.CommonAPI.Utils
|
||||||
alias Pleroma.Web.MastodonAPI.StatusView
|
alias Pleroma.Web.MastodonAPI.StatusView
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
def render(
|
def render(
|
||||||
"show.json",
|
"show.json",
|
||||||
%{
|
%{
|
||||||
|
@ -51,7 +53,7 @@ def render("index.json", opts) do
|
||||||
end
|
end
|
||||||
|
|
||||||
defp put_idempotency_key(data) do
|
defp put_idempotency_key(data) do
|
||||||
with {:ok, idempotency_key} <- Cachex.get(:chat_message_id_idempotency_key_cache, data.id) do
|
with {:ok, idempotency_key} <- @cachex.get(:chat_message_id_idempotency_key_cache, data.id) do
|
||||||
data
|
data
|
||||||
|> Maps.put_if_present(:idempotency_key, idempotency_key)
|
|> Maps.put_if_present(:idempotency_key, idempotency_key)
|
||||||
else
|
else
|
||||||
|
|
|
@ -41,6 +41,8 @@ def index(conn, _params) do
|
||||||
|
|
||||||
@defaults %{ttl: nil, query_params: true}
|
@defaults %{ttl: nil, query_params: true}
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
@impl true
|
@impl true
|
||||||
def init([]), do: @defaults
|
def init([]), do: @defaults
|
||||||
|
|
||||||
|
@ -53,7 +55,7 @@ def init(opts) do
|
||||||
def call(%{method: "GET"} = conn, opts) do
|
def call(%{method: "GET"} = conn, opts) do
|
||||||
key = cache_key(conn, opts)
|
key = cache_key(conn, opts)
|
||||||
|
|
||||||
case Cachex.get(:web_resp_cache, key) do
|
case @cachex.get(:web_resp_cache, key) do
|
||||||
{:ok, nil} ->
|
{:ok, nil} ->
|
||||||
cache_resp(conn, opts)
|
cache_resp(conn, opts)
|
||||||
|
|
||||||
|
@ -97,11 +99,11 @@ defp cache_resp(conn, opts) do
|
||||||
|
|
||||||
conn =
|
conn =
|
||||||
unless opts[:tracking_fun] do
|
unless opts[:tracking_fun] do
|
||||||
Cachex.put(:web_resp_cache, key, {content_type, body}, ttl: ttl)
|
@cachex.put(:web_resp_cache, key, {content_type, body}, ttl: ttl)
|
||||||
conn
|
conn
|
||||||
else
|
else
|
||||||
tracking_fun_data = Map.get(conn.assigns, :tracking_fun_data, nil)
|
tracking_fun_data = Map.get(conn.assigns, :tracking_fun_data, nil)
|
||||||
Cachex.put(:web_resp_cache, key, {content_type, body, tracking_fun_data}, ttl: ttl)
|
@cachex.put(:web_resp_cache, key, {content_type, body, tracking_fun_data}, ttl: ttl)
|
||||||
|
|
||||||
opts.tracking_fun.(conn, tracking_fun_data)
|
opts.tracking_fun.(conn, tracking_fun_data)
|
||||||
end
|
end
|
||||||
|
|
|
@ -8,6 +8,8 @@ defmodule Pleroma.Web.Plugs.IdempotencyPlug do
|
||||||
|
|
||||||
@behaviour Plug
|
@behaviour Plug
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
@impl true
|
@impl true
|
||||||
def init(opts), do: opts
|
def init(opts), do: opts
|
||||||
|
|
||||||
|
@ -25,7 +27,7 @@ def call(%{method: method} = conn, _) when method in ["POST", "PUT", "PATCH"] do
|
||||||
def call(conn, _), do: conn
|
def call(conn, _), do: conn
|
||||||
|
|
||||||
def process_request(conn, key) do
|
def process_request(conn, key) do
|
||||||
case Cachex.get(:idempotency_cache, key) do
|
case @cachex.get(:idempotency_cache, key) do
|
||||||
{:ok, nil} ->
|
{:ok, nil} ->
|
||||||
cache_resposnse(conn, key)
|
cache_resposnse(conn, key)
|
||||||
|
|
||||||
|
@ -43,7 +45,7 @@ defp cache_resposnse(conn, key) do
|
||||||
content_type = get_content_type(conn)
|
content_type = get_content_type(conn)
|
||||||
|
|
||||||
record = {request_id, content_type, conn.status, conn.resp_body}
|
record = {request_id, content_type, conn.status, conn.resp_body}
|
||||||
{:ok, _} = Cachex.put(:idempotency_cache, key, record)
|
{:ok, _} = @cachex.put(:idempotency_cache, key, record)
|
||||||
|
|
||||||
conn
|
conn
|
||||||
|> put_resp_header("idempotency-key", key)
|
|> put_resp_header("idempotency-key", key)
|
||||||
|
|
|
@ -72,6 +72,8 @@ defmodule Pleroma.Web.Plugs.RateLimiter do
|
||||||
|
|
||||||
require Logger
|
require Logger
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
@doc false
|
@doc false
|
||||||
def init(plug_opts) do
|
def init(plug_opts) do
|
||||||
plug_opts
|
plug_opts
|
||||||
|
@ -124,7 +126,7 @@ def inspect_bucket(conn, bucket_name_root, plug_opts) do
|
||||||
key_name = make_key_name(action_settings)
|
key_name = make_key_name(action_settings)
|
||||||
limit = get_limits(action_settings)
|
limit = get_limits(action_settings)
|
||||||
|
|
||||||
case Cachex.get(bucket_name, key_name) do
|
case @cachex.get(bucket_name, key_name) do
|
||||||
{:error, :no_cache} ->
|
{:error, :no_cache} ->
|
||||||
@inspect_bucket_not_found
|
@inspect_bucket_not_found
|
||||||
|
|
||||||
|
@ -157,7 +159,7 @@ defp check_rate(action_settings) do
|
||||||
key_name = make_key_name(action_settings)
|
key_name = make_key_name(action_settings)
|
||||||
limit = get_limits(action_settings)
|
limit = get_limits(action_settings)
|
||||||
|
|
||||||
case Cachex.get_and_update(bucket_name, key_name, &increment_value(&1, limit)) do
|
case @cachex.get_and_update(bucket_name, key_name, &increment_value(&1, limit)) do
|
||||||
{:commit, value} ->
|
{:commit, value} ->
|
||||||
{:ok, value}
|
{:ok, value}
|
||||||
|
|
||||||
|
|
|
@ -12,8 +12,9 @@ defmodule Pleroma.Web.RelMe do
|
||||||
if Pleroma.Config.get(:env) == :test do
|
if Pleroma.Config.get(:env) == :test do
|
||||||
def parse(url) when is_binary(url), do: parse_url(url)
|
def parse(url) when is_binary(url), do: parse_url(url)
|
||||||
else
|
else
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
def parse(url) when is_binary(url) do
|
def parse(url) when is_binary(url) do
|
||||||
Cachex.fetch!(:rel_me_cache, url, fn _ ->
|
@cachex.fetch!(:rel_me_cache, url, fn _ ->
|
||||||
{:commit, parse_url(url)}
|
{:commit, parse_url(url)}
|
||||||
end)
|
end)
|
||||||
rescue
|
rescue
|
||||||
|
|
|
@ -5,6 +5,8 @@
|
||||||
defmodule Pleroma.Web.RichMedia.Parser do
|
defmodule Pleroma.Web.RichMedia.Parser do
|
||||||
require Logger
|
require Logger
|
||||||
|
|
||||||
|
@cachex Pleroma.Config.get([:cachex, :provider], Cachex)
|
||||||
|
|
||||||
defp parsers do
|
defp parsers do
|
||||||
Pleroma.Config.get([:rich_media, :parsers])
|
Pleroma.Config.get([:rich_media, :parsers])
|
||||||
end
|
end
|
||||||
|
@ -24,7 +26,7 @@ def parse(url) do
|
||||||
end
|
end
|
||||||
|
|
||||||
defp get_cached_or_parse(url) do
|
defp get_cached_or_parse(url) do
|
||||||
case Cachex.fetch(:rich_media_cache, url, fn ->
|
case @cachex.fetch(:rich_media_cache, url, fn ->
|
||||||
case parse_url(url) do
|
case parse_url(url) do
|
||||||
{:ok, _} = res ->
|
{:ok, _} = res ->
|
||||||
{:commit, res}
|
{:commit, res}
|
||||||
|
@ -64,7 +66,7 @@ defp set_error_ttl(_url, {:content_type, _}), do: :ok
|
||||||
|
|
||||||
defp set_error_ttl(url, _reason) do
|
defp set_error_ttl(url, _reason) do
|
||||||
ttl = Pleroma.Config.get([:rich_media, :failure_backoff], 60_000)
|
ttl = Pleroma.Config.get([:rich_media, :failure_backoff], 60_000)
|
||||||
Cachex.expire(:rich_media_cache, url, ttl)
|
@cachex.expire(:rich_media_cache, url, ttl)
|
||||||
:ok
|
:ok
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -106,7 +108,7 @@ def set_ttl_based_on_image(data, url) do
|
||||||
{:ok, ttl} when is_number(ttl) ->
|
{:ok, ttl} when is_number(ttl) ->
|
||||||
ttl = ttl * 1000
|
ttl = ttl * 1000
|
||||||
|
|
||||||
case Cachex.expire_at(:rich_media_cache, url, ttl) do
|
case @cachex.expire_at(:rich_media_cache, url, ttl) do
|
||||||
{:ok, true} -> {:ok, ttl}
|
{:ok, true} -> {:ok, ttl}
|
||||||
{:ok, false} -> {:error, :no_key}
|
{:ok, false} -> {:error, :no_key}
|
||||||
end
|
end
|
||||||
|
|
2
mix.exs
2
mix.exs
|
@ -211,7 +211,7 @@ defp deps do
|
||||||
git: "https://git.pleroma.social/pleroma/elixir-libraries/hackney.git",
|
git: "https://git.pleroma.social/pleroma/elixir-libraries/hackney.git",
|
||||||
ref: "7d7119f0651515d6d7669c78393fd90950a3ec6e",
|
ref: "7d7119f0651515d6d7669c78393fd90950a3ec6e",
|
||||||
override: true},
|
override: true},
|
||||||
{:mox, "~> 0.5", only: :test},
|
{:mox, "~> 1.0", only: :test},
|
||||||
{:websocket_client, git: "https://github.com/jeremyong/websocket_client.git", only: :test}
|
{:websocket_client, git: "https://github.com/jeremyong/websocket_client.git", only: :test}
|
||||||
] ++ oauth_deps()
|
] ++ oauth_deps()
|
||||||
end
|
end
|
||||||
|
|
2
mix.lock
2
mix.lock
|
@ -76,7 +76,7 @@
|
||||||
"mochiweb": {:hex, :mochiweb, "2.18.0", "eb55f1db3e6e960fac4e6db4e2db9ec3602cc9f30b86cd1481d56545c3145d2e", [:rebar3], [], "hexpm"},
|
"mochiweb": {:hex, :mochiweb, "2.18.0", "eb55f1db3e6e960fac4e6db4e2db9ec3602cc9f30b86cd1481d56545c3145d2e", [:rebar3], [], "hexpm"},
|
||||||
"mock": {:hex, :mock, "0.3.5", "feb81f52b8dcf0a0d65001d2fec459f6b6a8c22562d94a965862f6cc066b5431", [:mix], [{:meck, "~> 0.8.13", [hex: :meck, repo: "hexpm", optional: false]}], "hexpm", "6fae404799408300f863550392635d8f7e3da6b71abdd5c393faf41b131c8728"},
|
"mock": {:hex, :mock, "0.3.5", "feb81f52b8dcf0a0d65001d2fec459f6b6a8c22562d94a965862f6cc066b5431", [:mix], [{:meck, "~> 0.8.13", [hex: :meck, repo: "hexpm", optional: false]}], "hexpm", "6fae404799408300f863550392635d8f7e3da6b71abdd5c393faf41b131c8728"},
|
||||||
"mogrify": {:hex, :mogrify, "0.7.4", "9b2496dde44b1ce12676f85d7dc531900939e6367bc537c7243a1b089435b32d", [:mix], [], "hexpm", "50d79e337fba6bc95bfbef918058c90f50b17eed9537771e61d4619488f099c3"},
|
"mogrify": {:hex, :mogrify, "0.7.4", "9b2496dde44b1ce12676f85d7dc531900939e6367bc537c7243a1b089435b32d", [:mix], [], "hexpm", "50d79e337fba6bc95bfbef918058c90f50b17eed9537771e61d4619488f099c3"},
|
||||||
"mox": {:hex, :mox, "0.5.2", "55a0a5ba9ccc671518d068c8dddd20eeb436909ea79d1799e2209df7eaa98b6c", [:mix], [], "hexpm", "df4310628cd628ee181df93f50ddfd07be3e5ecc30232d3b6aadf30bdfe6092b"},
|
"mox": {:hex, :mox, "1.0.0", "4b3c7005173f47ff30641ba044eb0fe67287743eec9bd9545e37f3002b0a9f8b", [:mix], [], "hexpm", "201b0a20b7abdaaab083e9cf97884950f8a30a1350a1da403b3145e213c6f4df"},
|
||||||
"myhtmlex": {:git, "https://git.pleroma.social/pleroma/myhtmlex.git", "ad0097e2f61d4953bfef20fb6abddf23b87111e6", [ref: "ad0097e2f61d4953bfef20fb6abddf23b87111e6", submodules: true]},
|
"myhtmlex": {:git, "https://git.pleroma.social/pleroma/myhtmlex.git", "ad0097e2f61d4953bfef20fb6abddf23b87111e6", [ref: "ad0097e2f61d4953bfef20fb6abddf23b87111e6", submodules: true]},
|
||||||
"nimble_parsec": {:hex, :nimble_parsec, "0.6.0", "32111b3bf39137144abd7ba1cce0914533b2d16ef35e8abc5ec8be6122944263", [:mix], [], "hexpm", "27eac315a94909d4dc68bc07a4a83e06c8379237c5ea528a9acff4ca1c873c52"},
|
"nimble_parsec": {:hex, :nimble_parsec, "0.6.0", "32111b3bf39137144abd7ba1cce0914533b2d16ef35e8abc5ec8be6122944263", [:mix], [], "hexpm", "27eac315a94909d4dc68bc07a4a83e06c8379237c5ea528a9acff4ca1c873c52"},
|
||||||
"nimble_pool": {:hex, :nimble_pool, "0.1.0", "ffa9d5be27eee2b00b0c634eb649aa27f97b39186fec3c493716c2a33e784ec6", [:mix], [], "hexpm", "343a1eaa620ddcf3430a83f39f2af499fe2370390d4f785cd475b4df5acaf3f9"},
|
"nimble_pool": {:hex, :nimble_pool, "0.1.0", "ffa9d5be27eee2b00b0c634eb649aa27f97b39186fec3c493716c2a33e784ec6", [:mix], [], "hexpm", "343a1eaa620ddcf3430a83f39f2af499fe2370390d4f785cd475b4df5acaf3f9"},
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Mix.Tasks.Pleroma.CountStatusesTest do
|
defmodule Mix.Tasks.Pleroma.CountStatusesTest do
|
||||||
|
# Uses log capture, has to stay synchronous
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase
|
||||||
|
|
||||||
alias Pleroma.User
|
alias Pleroma.User
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Mix.Tasks.Pleroma.DatabaseTest do
|
defmodule Mix.Tasks.Pleroma.DatabaseTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
use Oban.Testing, repo: Pleroma.Repo
|
use Oban.Testing, repo: Pleroma.Repo
|
||||||
|
|
||||||
alias Pleroma.Activity
|
alias Pleroma.Activity
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-onl
|
# SPDX-License-Identifier: AGPL-3.0-onl
|
||||||
|
|
||||||
defmodule Mix.Tasks.Pleroma.Ecto.MigrateTest do
|
defmodule Mix.Tasks.Pleroma.Ecto.MigrateTest do
|
||||||
use Pleroma.DataCase, async: true
|
use Pleroma.DataCase
|
||||||
import ExUnit.CaptureLog
|
import ExUnit.CaptureLog
|
||||||
require Logger
|
require Logger
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Mix.Tasks.Pleroma.Ecto.RollbackTest do
|
defmodule Mix.Tasks.Pleroma.Ecto.RollbackTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
import ExUnit.CaptureLog
|
import ExUnit.CaptureLog
|
||||||
require Logger
|
require Logger
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,8 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Mix.Tasks.Pleroma.InstanceTest do
|
defmodule Mix.Tasks.Pleroma.InstanceTest do
|
||||||
use ExUnit.Case
|
# Modifies the Application Environment, has to stay synchronous.
|
||||||
|
use Pleroma.DataCase
|
||||||
|
|
||||||
setup do
|
setup do
|
||||||
File.mkdir_p!(tmp_path())
|
File.mkdir_p!(tmp_path())
|
||||||
|
@ -15,15 +16,17 @@ defmodule Mix.Tasks.Pleroma.InstanceTest do
|
||||||
if File.exists?(static_dir) do
|
if File.exists?(static_dir) do
|
||||||
File.rm_rf(Path.join(static_dir, "robots.txt"))
|
File.rm_rf(Path.join(static_dir, "robots.txt"))
|
||||||
end
|
end
|
||||||
|
|
||||||
Pleroma.Config.put([:instance, :static_dir], static_dir)
|
|
||||||
end)
|
end)
|
||||||
|
|
||||||
|
# Is being modified by the mix task.
|
||||||
|
clear_config([:instance, :static_dir])
|
||||||
|
|
||||||
:ok
|
:ok
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@uuid Ecto.UUID.generate()
|
||||||
defp tmp_path do
|
defp tmp_path do
|
||||||
"/tmp/generated_files/"
|
"/tmp/generated_files/#{@uuid}/"
|
||||||
end
|
end
|
||||||
|
|
||||||
test "running gen" do
|
test "running gen" do
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Mix.Tasks.Pleroma.RefreshCounterCacheTest do
|
defmodule Mix.Tasks.Pleroma.RefreshCounterCacheTest do
|
||||||
|
# Uses log capture, has to stay synchronous
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase
|
||||||
alias Pleroma.Web.CommonAPI
|
alias Pleroma.Web.CommonAPI
|
||||||
import ExUnit.CaptureIO, only: [capture_io: 1]
|
import ExUnit.CaptureIO, only: [capture_io: 1]
|
||||||
|
|
|
@ -100,7 +100,7 @@ test "unfollow when relay is dead" do
|
||||||
end)
|
end)
|
||||||
|
|
||||||
Pleroma.Repo.delete(user)
|
Pleroma.Repo.delete(user)
|
||||||
Cachex.clear(:user_cache)
|
User.invalidate_cache(user)
|
||||||
|
|
||||||
Mix.Tasks.Pleroma.Relay.run(["unfollow", target_instance])
|
Mix.Tasks.Pleroma.Relay.run(["unfollow", target_instance])
|
||||||
|
|
||||||
|
@ -137,7 +137,7 @@ test "force unfollow when relay is dead" do
|
||||||
end)
|
end)
|
||||||
|
|
||||||
Pleroma.Repo.delete(user)
|
Pleroma.Repo.delete(user)
|
||||||
Cachex.clear(:user_cache)
|
User.invalidate_cache(user)
|
||||||
|
|
||||||
Mix.Tasks.Pleroma.Relay.run(["unfollow", target_instance, "--force"])
|
Mix.Tasks.Pleroma.Relay.run(["unfollow", target_instance, "--force"])
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Activity.Ir.TopicsTest do
|
defmodule Pleroma.Activity.Ir.TopicsTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.Activity
|
alias Pleroma.Activity
|
||||||
alias Pleroma.Activity.Ir.Topics
|
alias Pleroma.Activity.Ir.Topics
|
||||||
|
|
|
@ -7,7 +7,7 @@ defmodule Pleroma.Activity.SearchTest do
|
||||||
alias Pleroma.Web.CommonAPI
|
alias Pleroma.Web.CommonAPI
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
test "it finds something" do
|
test "it finds something" do
|
||||||
user = insert(:user)
|
user = insert(:user)
|
||||||
|
|
|
@ -15,6 +15,7 @@ defmodule Pleroma.ApplicationRequirementsTest do
|
||||||
describe "check_repo_pool_size!/1" do
|
describe "check_repo_pool_size!/1" do
|
||||||
test "raises if the pool size is unexpected" do
|
test "raises if the pool size is unexpected" do
|
||||||
clear_config([Pleroma.Repo, :pool_size], 11)
|
clear_config([Pleroma.Repo, :pool_size], 11)
|
||||||
|
clear_config([:dangerzone, :override_repo_pool_size], false)
|
||||||
|
|
||||||
assert_raise Pleroma.ApplicationRequirements.VerifyError,
|
assert_raise Pleroma.ApplicationRequirements.VerifyError,
|
||||||
"Repo.pool_size different than recommended value.",
|
"Repo.pool_size different than recommended value.",
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.BBS.HandlerTest do
|
defmodule Pleroma.BBS.HandlerTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
alias Pleroma.Activity
|
alias Pleroma.Activity
|
||||||
alias Pleroma.BBS.Handler
|
alias Pleroma.BBS.Handler
|
||||||
alias Pleroma.Object
|
alias Pleroma.Object
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.BookmarkTest do
|
defmodule Pleroma.BookmarkTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
alias Pleroma.Bookmark
|
alias Pleroma.Bookmark
|
||||||
alias Pleroma.Web.CommonAPI
|
alias Pleroma.Web.CommonAPI
|
||||||
|
|
|
@ -80,7 +80,6 @@ test "validate" do
|
||||||
|
|
||||||
assert is_binary(answer)
|
assert is_binary(answer)
|
||||||
assert :ok = Captcha.validate(token, "63615261b77f5354fb8c4e4986477555", answer)
|
assert :ok = Captcha.validate(token, "63615261b77f5354fb8c4e4986477555", answer)
|
||||||
Cachex.del(:used_captcha_cache, token)
|
|
||||||
end
|
end
|
||||||
|
|
||||||
test "doesn't validate invalid answer" do
|
test "doesn't validate invalid answer" do
|
||||||
|
|
|
@ -73,7 +73,8 @@ test "a returning chat will have an updated `update_at` field" do
|
||||||
other_user = insert(:user)
|
other_user = insert(:user)
|
||||||
|
|
||||||
{:ok, chat} = Chat.bump_or_create(user.id, other_user.ap_id)
|
{:ok, chat} = Chat.bump_or_create(user.id, other_user.ap_id)
|
||||||
:timer.sleep(1500)
|
{:ok, chat} = time_travel(chat, -2)
|
||||||
|
|
||||||
{:ok, chat_two} = Chat.bump_or_create(user.id, other_user.ap_id)
|
{:ok, chat_two} = Chat.bump_or_create(user.id, other_user.ap_id)
|
||||||
|
|
||||||
assert chat.id == chat_two.id
|
assert chat.id == chat_two.id
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.ConfigTest do
|
defmodule Pleroma.ConfigTest do
|
||||||
use ExUnit.Case
|
use Pleroma.DataCase
|
||||||
|
|
||||||
test "get/1 with an atom" do
|
test "get/1 with an atom" do
|
||||||
assert Pleroma.Config.get(:instance) == Application.get_env(:pleroma, :instance)
|
assert Pleroma.Config.get(:instance) == Application.get_env(:pleroma, :instance)
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Conversation.ParticipationTest do
|
defmodule Pleroma.Conversation.ParticipationTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
alias Pleroma.Conversation
|
alias Pleroma.Conversation
|
||||||
alias Pleroma.Conversation.Participation
|
alias Pleroma.Conversation.Participation
|
||||||
|
@ -96,12 +96,11 @@ test "it creates a participation for a conversation and a user" do
|
||||||
{:ok, %Participation{} = participation} =
|
{:ok, %Participation{} = participation} =
|
||||||
Participation.create_for_user_and_conversation(user, conversation)
|
Participation.create_for_user_and_conversation(user, conversation)
|
||||||
|
|
||||||
|
{:ok, participation} = time_travel(participation, -2)
|
||||||
|
|
||||||
assert participation.user_id == user.id
|
assert participation.user_id == user.id
|
||||||
assert participation.conversation_id == conversation.id
|
assert participation.conversation_id == conversation.id
|
||||||
|
|
||||||
# Needed because updated_at is accurate down to a second
|
|
||||||
:timer.sleep(1000)
|
|
||||||
|
|
||||||
# Creating again returns the same participation
|
# Creating again returns the same participation
|
||||||
{:ok, %Participation{} = participation_two} =
|
{:ok, %Participation{} = participation_two} =
|
||||||
Participation.create_for_user_and_conversation(user, conversation)
|
Participation.create_for_user_and_conversation(user, conversation)
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
# Copyright © 2020 Pleroma Authors <https://pleroma.social/>
|
# Copyright © 2020 Pleroma Authors <https://pleroma.social/>
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
defmodule Pleroma.EarmarkRendererTest do
|
defmodule Pleroma.EarmarkRendererTest do
|
||||||
use ExUnit.Case
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
test "Paragraph" do
|
test "Paragraph" do
|
||||||
code = ~s[Hello\n\nWorld!]
|
code = ~s[Hello\n\nWorld!]
|
||||||
|
|
|
@ -4,7 +4,7 @@
|
||||||
|
|
||||||
defmodule Pleroma.EctoType.ActivityPub.ObjectValidators.DateTimeTest do
|
defmodule Pleroma.EctoType.ActivityPub.ObjectValidators.DateTimeTest do
|
||||||
alias Pleroma.EctoType.ActivityPub.ObjectValidators.DateTime
|
alias Pleroma.EctoType.ActivityPub.ObjectValidators.DateTime
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
test "it validates an xsd:Datetime" do
|
test "it validates an xsd:Datetime" do
|
||||||
valid_strings = [
|
valid_strings = [
|
||||||
|
|
|
@ -4,7 +4,7 @@
|
||||||
|
|
||||||
defmodule Pleroma.EctoType.ActivityPub.ObjectValidators.ObjectIDTest do
|
defmodule Pleroma.EctoType.ActivityPub.ObjectValidators.ObjectIDTest do
|
||||||
alias Pleroma.EctoType.ActivityPub.ObjectValidators.ObjectID
|
alias Pleroma.EctoType.ActivityPub.ObjectValidators.ObjectID
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
@uris [
|
@uris [
|
||||||
"http://lain.com/users/lain",
|
"http://lain.com/users/lain",
|
||||||
|
|
|
@ -4,7 +4,7 @@
|
||||||
|
|
||||||
defmodule Pleroma.EctoType.ActivityPub.ObjectValidators.RecipientsTest do
|
defmodule Pleroma.EctoType.ActivityPub.ObjectValidators.RecipientsTest do
|
||||||
alias Pleroma.EctoType.ActivityPub.ObjectValidators.Recipients
|
alias Pleroma.EctoType.ActivityPub.ObjectValidators.Recipients
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
test "it asserts that all elements of the list are object ids" do
|
test "it asserts that all elements of the list are object ids" do
|
||||||
list = ["https://lain.com/users/lain", "invalid"]
|
list = ["https://lain.com/users/lain", "invalid"]
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.EctoType.ActivityPub.ObjectValidators.SafeTextTest do
|
defmodule Pleroma.EctoType.ActivityPub.ObjectValidators.SafeTextTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.EctoType.ActivityPub.ObjectValidators.SafeText
|
alias Pleroma.EctoType.ActivityPub.ObjectValidators.SafeText
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Emails.AdminEmailTest do
|
defmodule Pleroma.Emails.AdminEmailTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
alias Pleroma.Emails.AdminEmail
|
alias Pleroma.Emails.AdminEmail
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Emails.UserEmailTest do
|
defmodule Pleroma.Emails.UserEmailTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.Emails.UserEmail
|
alias Pleroma.Emails.UserEmail
|
||||||
alias Pleroma.Web.Endpoint
|
alias Pleroma.Web.Endpoint
|
||||||
|
|
|
@ -4,7 +4,7 @@
|
||||||
|
|
||||||
defmodule Pleroma.Emoji.FormatterTest do
|
defmodule Pleroma.Emoji.FormatterTest do
|
||||||
alias Pleroma.Emoji.Formatter
|
alias Pleroma.Emoji.Formatter
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
describe "emojify" do
|
describe "emojify" do
|
||||||
test "it adds cool emoji" do
|
test "it adds cool emoji" do
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Emoji.PackTest do
|
defmodule Pleroma.Emoji.PackTest do
|
||||||
use ExUnit.Case, async: true
|
use Pleroma.DataCase
|
||||||
alias Pleroma.Emoji.Pack
|
alias Pleroma.Emoji.Pack
|
||||||
|
|
||||||
@emoji_path Path.join(
|
@emoji_path Path.join(
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.EmojiTest do
|
defmodule Pleroma.EmojiTest do
|
||||||
use ExUnit.Case
|
use ExUnit.Case, async: true
|
||||||
alias Pleroma.Emoji
|
alias Pleroma.Emoji
|
||||||
|
|
||||||
describe "is_unicode_emoji?/1" do
|
describe "is_unicode_emoji?/1" do
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.FilterTest do
|
defmodule Pleroma.FilterTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.FollowingRelationshipTest do
|
defmodule Pleroma.FollowingRelationshipTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.FollowingRelationship
|
alias Pleroma.FollowingRelationship
|
||||||
alias Pleroma.Web.ActivityPub.InternalFetchActor
|
alias Pleroma.Web.ActivityPub.InternalFetchActor
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.HealthcheckTest do
|
defmodule Pleroma.HealthcheckTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
alias Pleroma.Healthcheck
|
alias Pleroma.Healthcheck
|
||||||
|
|
||||||
test "system_info/0" do
|
test "system_info/0" do
|
||||||
|
|
|
@ -6,7 +6,7 @@ defmodule Pleroma.HTMLTest do
|
||||||
alias Pleroma.HTML
|
alias Pleroma.HTML
|
||||||
alias Pleroma.Object
|
alias Pleroma.Object
|
||||||
alias Pleroma.Web.CommonAPI
|
alias Pleroma.Web.CommonAPI
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.HTTP.AdapterHelper.GunTest do
|
defmodule Pleroma.HTTP.AdapterHelper.GunTest do
|
||||||
use ExUnit.Case, async: true
|
use ExUnit.Case
|
||||||
use Pleroma.Tests.Helpers
|
use Pleroma.Tests.Helpers
|
||||||
|
|
||||||
import Mox
|
import Mox
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Integration.MastodonWebsocketTest do
|
defmodule Pleroma.Integration.MastodonWebsocketTest do
|
||||||
|
# Needs a streamer, needs to stay synchronous
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase
|
||||||
|
|
||||||
import ExUnit.CaptureLog
|
import ExUnit.CaptureLog
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.KeysTest do
|
defmodule Pleroma.KeysTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.Keys
|
alias Pleroma.Keys
|
||||||
|
|
||||||
|
|
|
@ -4,7 +4,7 @@
|
||||||
|
|
||||||
defmodule Pleroma.ListTest do
|
defmodule Pleroma.ListTest do
|
||||||
alias Pleroma.Repo
|
alias Pleroma.Repo
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.MarkerTest do
|
defmodule Pleroma.MarkerTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
alias Pleroma.Marker
|
alias Pleroma.Marker
|
||||||
|
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.MFA.BackupCodesTest do
|
defmodule Pleroma.MFA.BackupCodesTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.MFA.BackupCodes
|
alias Pleroma.MFA.BackupCodes
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.MFA.TOTPTest do
|
defmodule Pleroma.MFA.TOTPTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.MFA.TOTP
|
alias Pleroma.MFA.TOTP
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.MFATest do
|
defmodule Pleroma.MFATest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
alias Pleroma.MFA
|
alias Pleroma.MFA
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.MigrationHelper.NotificationBackfillTest do
|
defmodule Pleroma.MigrationHelper.NotificationBackfillTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.Activity
|
alias Pleroma.Activity
|
||||||
alias Pleroma.MigrationHelper.NotificationBackfill
|
alias Pleroma.MigrationHelper.NotificationBackfill
|
||||||
|
|
|
@ -6,7 +6,7 @@ defmodule Pleroma.ModerationLogTest do
|
||||||
alias Pleroma.Activity
|
alias Pleroma.Activity
|
||||||
alias Pleroma.ModerationLog
|
alias Pleroma.ModerationLog
|
||||||
|
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.PaginationTest do
|
defmodule Pleroma.PaginationTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.RegistrationTest do
|
defmodule Pleroma.RegistrationTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
|
|
|
@ -4,7 +4,7 @@
|
||||||
|
|
||||||
defmodule Pleroma.Repo.Migrations.FixLegacyTagsTest do
|
defmodule Pleroma.Repo.Migrations.FixLegacyTagsTest do
|
||||||
alias Pleroma.User
|
alias Pleroma.User
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
import Pleroma.Tests.Helpers
|
import Pleroma.Tests.Helpers
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Repo.Migrations.MoveWelcomeSettingsTest do
|
defmodule Pleroma.Repo.Migrations.MoveWelcomeSettingsTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
import Pleroma.Tests.Helpers
|
import Pleroma.Tests.Helpers
|
||||||
alias Pleroma.ConfigDB
|
alias Pleroma.ConfigDB
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.RepoTest do
|
defmodule Pleroma.RepoTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
alias Pleroma.User
|
alias Pleroma.User
|
||||||
|
|
|
@ -4,7 +4,7 @@
|
||||||
|
|
||||||
defmodule Pleroma.ReportNoteTest do
|
defmodule Pleroma.ReportNoteTest do
|
||||||
alias Pleroma.ReportNote
|
alias Pleroma.ReportNote
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
test "create/3" do
|
test "create/3" do
|
||||||
|
|
|
@ -3,8 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.ReverseProxyTest do
|
defmodule Pleroma.ReverseProxyTest do
|
||||||
use Pleroma.Web.ConnCase, async: true
|
use Pleroma.Web.ConnCase
|
||||||
|
|
||||||
import ExUnit.CaptureLog
|
import ExUnit.CaptureLog
|
||||||
import Mox
|
import Mox
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.SafeJsonbSetTest do
|
defmodule Pleroma.SafeJsonbSetTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
test "it doesn't wipe the object when asked to set the value to NULL" do
|
test "it doesn't wipe the object when asked to set the value to NULL" do
|
||||||
assert %{rows: [[%{"key" => "value", "test" => nil}]]} =
|
assert %{rows: [[%{"key" => "value", "test" => nil}]]} =
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.StatsTest do
|
defmodule Pleroma.StatsTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Upload.Filter.DedupeTest do
|
defmodule Pleroma.Upload.Filter.DedupeTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.Upload
|
alias Pleroma.Upload
|
||||||
alias Pleroma.Upload.Filter.Dedupe
|
alias Pleroma.Upload.Filter.Dedupe
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Upload.Filter.ExiftoolTest do
|
defmodule Pleroma.Upload.Filter.ExiftoolTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
alias Pleroma.Upload.Filter
|
alias Pleroma.Upload.Filter
|
||||||
|
|
||||||
test "apply exiftool filter" do
|
test "apply exiftool filter" do
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Uploaders.LocalTest do
|
defmodule Pleroma.Uploaders.LocalTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
alias Pleroma.Uploaders.Local
|
alias Pleroma.Uploaders.Local
|
||||||
|
|
||||||
describe "get_file/1" do
|
describe "get_file/1" do
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.User.NotificationSettingTest do
|
defmodule Pleroma.User.NotificationSettingTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.User.NotificationSetting
|
alias Pleroma.User.NotificationSetting
|
||||||
|
|
||||||
|
|
|
@ -5,7 +5,7 @@
|
||||||
defmodule Pleroma.UserRelationshipTest do
|
defmodule Pleroma.UserRelationshipTest do
|
||||||
alias Pleroma.UserRelationship
|
alias Pleroma.UserRelationship
|
||||||
|
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Web.ActivityPub.MRF.AntiFollowbotPolicyTest do
|
defmodule Pleroma.Web.ActivityPub.MRF.AntiFollowbotPolicyTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
alias Pleroma.Web.ActivityPub.MRF.AntiFollowbotPolicy
|
alias Pleroma.Web.ActivityPub.MRF.AntiFollowbotPolicy
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Web.ActivityPub.MRF.EnsureRePrependedTest do
|
defmodule Pleroma.Web.ActivityPub.MRF.EnsureRePrependedTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.Activity
|
alias Pleroma.Activity
|
||||||
alias Pleroma.Object
|
alias Pleroma.Object
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Web.ActivityPub.MRF.ForceBotUnlistedPolicyTest do
|
defmodule Pleroma.Web.ActivityPub.MRF.ForceBotUnlistedPolicyTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
alias Pleroma.Web.ActivityPub.MRF.ForceBotUnlistedPolicy
|
alias Pleroma.Web.ActivityPub.MRF.ForceBotUnlistedPolicy
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Web.ActivityPub.MRF.NoPlaceholderTextPolicyTest do
|
defmodule Pleroma.Web.ActivityPub.MRF.NoPlaceholderTextPolicyTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
alias Pleroma.Web.ActivityPub.MRF.NoPlaceholderTextPolicy
|
alias Pleroma.Web.ActivityPub.MRF.NoPlaceholderTextPolicy
|
||||||
|
|
||||||
test "it clears content object" do
|
test "it clears content object" do
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Web.ActivityPub.MRF.NormalizeMarkupTest do
|
defmodule Pleroma.Web.ActivityPub.MRF.NormalizeMarkupTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
alias Pleroma.Web.ActivityPub.MRF.NormalizeMarkup
|
alias Pleroma.Web.ActivityPub.MRF.NormalizeMarkup
|
||||||
|
|
||||||
@html_sample """
|
@html_sample """
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Web.ActivityPub.MRF.TagPolicyTest do
|
defmodule Pleroma.Web.ActivityPub.MRF.TagPolicyTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
import Pleroma.Factory
|
import Pleroma.Factory
|
||||||
|
|
||||||
alias Pleroma.Web.ActivityPub.MRF.TagPolicy
|
alias Pleroma.Web.ActivityPub.MRF.TagPolicy
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Web.ActivityPub.ObjectValidators.AcceptValidationTest do
|
defmodule Pleroma.Web.ActivityPub.ObjectValidators.AcceptValidationTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.Web.ActivityPub.Builder
|
alias Pleroma.Web.ActivityPub.Builder
|
||||||
alias Pleroma.Web.ActivityPub.ObjectValidator
|
alias Pleroma.Web.ActivityPub.ObjectValidator
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Web.ActivityPub.ObjectValidators.AnnounceValidationTest do
|
defmodule Pleroma.Web.ActivityPub.ObjectValidators.AnnounceValidationTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.Object
|
alias Pleroma.Object
|
||||||
alias Pleroma.Web.ActivityPub.Builder
|
alias Pleroma.Web.ActivityPub.Builder
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Web.ActivityPub.ObjectValidators.ArticleNoteValidatorTest do
|
defmodule Pleroma.Web.ActivityPub.ObjectValidators.ArticleNoteValidatorTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.Web.ActivityPub.ObjectValidators.ArticleNoteValidator
|
alias Pleroma.Web.ActivityPub.ObjectValidators.ArticleNoteValidator
|
||||||
alias Pleroma.Web.ActivityPub.Utils
|
alias Pleroma.Web.ActivityPub.Utils
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Web.ActivityPub.ObjectValidators.AttachmentValidatorTest do
|
defmodule Pleroma.Web.ActivityPub.ObjectValidators.AttachmentValidatorTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.Web.ActivityPub.ActivityPub
|
alias Pleroma.Web.ActivityPub.ActivityPub
|
||||||
alias Pleroma.Web.ActivityPub.ObjectValidators.AttachmentValidator
|
alias Pleroma.Web.ActivityPub.ObjectValidators.AttachmentValidator
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
# SPDX-License-Identifier: AGPL-3.0-only
|
# SPDX-License-Identifier: AGPL-3.0-only
|
||||||
|
|
||||||
defmodule Pleroma.Web.ActivityPub.ObjectValidators.BlockValidationTest do
|
defmodule Pleroma.Web.ActivityPub.ObjectValidators.BlockValidationTest do
|
||||||
use Pleroma.DataCase
|
use Pleroma.DataCase, async: true
|
||||||
|
|
||||||
alias Pleroma.Web.ActivityPub.Builder
|
alias Pleroma.Web.ActivityPub.Builder
|
||||||
alias Pleroma.Web.ActivityPub.ObjectValidator
|
alias Pleroma.Web.ActivityPub.ObjectValidator
|
||||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue