Merge branch 'develop' of upstream into froth

This commit is contained in:
Sam Therapy 2022-11-15 15:59:29 +01:00
commit cecdecf083
Signed by: sam
GPG Key ID: 4D8B07C18F31ACBD
70 changed files with 7086 additions and 250 deletions

1
.gitignore vendored
View File

@ -48,6 +48,7 @@ docs/generated_config.md
# Code test coverage
/cover
/Elixir.*.coverdata
/coverage.xml
.idea
pleroma.iml

View File

@ -5,6 +5,7 @@ variables: &global_variables
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
DB_HOST: postgres
DB_PORT: 5432
MIX_ENV: test
cache: &global_cache_policy
@ -84,7 +85,13 @@ unit-testing:
script:
- mix ecto.create
- mix ecto.migrate
- mix coveralls --preload-modules
- mix test --cover --preload-modules
coverage: '/^Line total: ([^ ]*%)$/'
artifacts:
reports:
coverage_report:
coverage_format: cobertura
path: coverage.xml
unit-testing-erratic:
stage: test

View File

@ -16,6 +16,8 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
- Uploadfilter `Pleroma.Upload.Filter.Exiftool` has been renamed to `Pleroma.Upload.Filter.Exiftool.StripLocation`
- **Breaking**: `/api/v1/pleroma/backups` endpoints now requires `read:backups` scope instead of `read:accounts`
- Updated the recommended pleroma.vcl configuration for Varnish to target Varnish 7.0+
- Set timeout values for Oban queues. The default is infinity and some operations may not time out on their own.
- Delete activities are federated at lowest priority
### Added
- `activeMonth` and `activeHalfyear` fields in NodeInfo usage.users object
@ -37,6 +39,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
- Uploadfilter `Pleroma.Upload.Filter.Exiftool.ReadDescription` returns description values to the FE so they can pre fill the image description field
- Added move account API
- Enable remote users to interact with posts
- Possibility to discover users like `user@example.org`, while Pleroma is working on `pleroma.example.org`. Additional configuration required.
### Fixed
- Subscription(Bell) Notifications: Don't create from Pipeline Ingested replies
@ -53,8 +56,10 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
- Fixed slow timelines when there are a lot of deactivated users
- Fixed account deletion API
- Fixed lowercase HTTP HEAD method in the Media Proxy Preview code
- Removed useless notification call on Delete activities
### Removed
- Quack, the logging backend that pushes to Slack channels
## 2.4.4 - 2022-08-19

View File

@ -40,6 +40,7 @@
password: "postgres",
database: "pleroma_benchmark",
hostname: System.get_env("DB_HOST") || "localhost",
port: System.get_env("DB_PORT") || "5432",
pool_size: 10
# Reduce hash rounds for testing

View File

@ -160,11 +160,6 @@
format: "$metadata[$level] $message",
metadata: [:request_id]
config :quack,
level: :warn,
meta: [:all],
webhook_url: "https://hooks.slack.com/services/YOUR-KEY-HERE"
config :mime, :types, %{
"application/xml" => ["xml"],
"application/xrd+xml" => ["xrd+xml"],
@ -228,6 +223,7 @@
max_pinned_statuses: 1,
attachment_links: false,
max_report_comment_size: 1000,
report_strip_status: true,
safe_dm_mentions: false,
healthcheck: false,
remote_post_retention_days: 90,
@ -756,12 +752,12 @@
"https://git.pleroma.social/pleroma/admin-fe/-/jobs/artifacts/${ref}/download?job=build",
"ref" => "develop"
},
"soapbox-fe" => %{
"name" => "soapbox-fe",
"git" => "https://gitlab.com/soapbox-pub/soapbox-fe",
"soapbox" => %{
"name" => "soapbox",
"git" => "https://gitlab.com/soapbox-pub/soapbox",
"build_url" =>
"https://gitlab.com/soapbox-pub/soapbox-fe/-/jobs/artifacts/${ref}/download?job=build-production",
"ref" => "v1.0.0",
"https://gitlab.com/soapbox-pub/soapbox/-/jobs/artifacts/${ref}/download?job=build-production",
"ref" => "v3.0.0-beta.1",
"build_dir" => "static"
},
"glitch-lily" => %{
@ -869,6 +865,8 @@
{Pleroma.Web.ActivityPub.MRF.MediaProxyWarmingPolicy, [max_running: 5, max_waiting: 5]}
]
config :pleroma, Pleroma.Web.WebFinger, domain: nil, update_nickname_on_user_fetch: true
# Import environment specific config. This must remain at the bottom
# of this file so it overrides the configuration defined above.
import_config "#{Mix.env()}.exs"

View File

@ -815,6 +815,13 @@
1_000
]
},
%{
key: :report_strip_status,
label: "Report strip status",
type: :boolean,
description:
"Strip associated statuses in reports to ids when closed/resolved, otherwise keep a copy"
},
%{
key: :safe_dm_mentions,
label: "Safe DM mentions",
@ -1190,45 +1197,6 @@
}
]
},
%{
group: :quack,
type: :group,
label: "Quack Logger",
description: "Quack-related settings",
children: [
%{
key: :level,
type: {:dropdown, :atom},
description: "Log level",
suggestions: [:debug, :info, :warn, :error]
},
%{
key: :meta,
type: {:list, :atom},
description: "Configure which metadata you want to report on",
suggestions: [
:application,
:module,
:file,
:function,
:line,
:pid,
:crash_reason,
:initial_call,
:registered_name,
:all,
:none
]
},
%{
key: :webhook_url,
label: "Webhook URL",
type: :string,
description: "Configure the Slack incoming webhook",
suggestions: ["https://hooks.slack.com/services/YOUR-KEY-HERE"]
}
]
},
%{
group: :pleroma,
key: :frontend_configurations,

View File

@ -18,6 +18,7 @@
password: System.fetch_env!("DB_PASS"),
database: System.get_env("DB_NAME", "pleroma"),
hostname: System.get_env("DB_HOST", "db"),
port: System.get_env("DB_PORT", "5432"),
pool_size: 10
# Configure web push notifications

View File

@ -47,6 +47,7 @@
password: "postgres",
database: "pleroma_test",
hostname: System.get_env("DB_HOST") || "localhost",
port: System.get_env("DB_PORT") || "5432",
pool: Ecto.Adapters.SQL.Sandbox,
pool_size: 50
@ -129,6 +130,8 @@
config :pleroma, :cachex, provider: Pleroma.CachexMock
config :pleroma, Pleroma.Web.WebFinger, update_nickname_on_user_fetch: false
config :pleroma, :side_effects,
ap_streamer: Pleroma.Web.ActivityPub.ActivityPubMock,
logger: Pleroma.LoggerMock

View File

@ -3,7 +3,7 @@
set -e
echo "-- Waiting for database..."
while ! pg_isready -U ${DB_USER:-pleroma} -d postgres://${DB_HOST:-db}:5432/${DB_NAME:-pleroma} -t 1; do
while ! pg_isready -U ${DB_USER:-pleroma} -d postgres://${DB_HOST:-db}:${DB_PORT:-5432}/${DB_NAME:-pleroma} -t 1; do
sleep 1s
done

View File

@ -22,7 +22,7 @@ Currently, known `<frontend>` values are:
- [kenoma](http://git.pleroma.social/lambadalambda/kenoma)
- [pleroma-fe](http://git.pleroma.social/pleroma/pleroma-fe)
- [fedi-fe](https://git.pleroma.social/pleroma/fedi-fe)
- [soapbox-fe](https://gitlab.com/soapbox-pub/soapbox-fe)
- [soapbox](https://gitlab.com/soapbox-pub/soapbox)
You can still install frontends that are not configured, see below.

View File

@ -49,6 +49,7 @@ To add configuration to your config file, you can copy it from the base config.
* `autofollowing_nicknames`: Set to nicknames of (local) users that automatically follows every newly registered user.
* `attachment_links`: Set to true to enable automatically adding attachment link text to statuses.
* `max_report_comment_size`: The maximum size of the report comment (Default: `1000`).
* `report_strip_status`: Strip associated statuses in reports to ids when closed/resolved, otherwise keep a copy.
* `safe_dm_mentions`: If set to true, only mentions at the beginning of a post will be used to address people in direct messages. This is to prevent accidental mentioning of people when talking about them (e.g. "@friend hey i really don't like @enemy"). Default: `false`.
* `healthcheck`: If set to true, system data will be shown on ``/api/v1/pleroma/healthcheck``.
* `remote_post_retention_days`: The default amount of days to retain remote posts when pruning the database.
@ -204,7 +205,7 @@ config :pleroma, :mrf_user_allowlist, %{
e.g., A value of 900 results in any post with a timestamp older than 15 minutes will be acted upon.
* `actions`: A list of actions to apply to the post:
* `:delist` removes the post from public timelines
* `:strip_followers` removes followers from the ActivityPub recipient list, ensuring they won't be delivered to home timelines
* `:strip_followers` removes followers from the ActivityPub recipient list, ensuring they won't be delivered to home timelines, additionally for followers-only it degrades to a direct message
* `:reject` rejects the message entirely
#### :mrf_steal_emoji

View File

@ -0,0 +1,62 @@
# How to use a different domain name for Pleroma and the users it serves
Pleroma users are primarily identified by a `user@example.org` handle, and you might want this identifier to be the same as your email or jabber account, for instance.
However, in this case, you are almost certainly serving some web content on `https://example.org` already, and you might want to use another domain (say `pleroma.example.org`) for Pleroma itself.
Pleroma supports that, but it might be tricky to set up, and any error might prevent you from federating with other instances.
*If you are already running Pleroma on `example.org`, it is no longer possible to move it to `pleroma.example.org`.*
## Account identifiers
It is important to understand that for federation purposes, a user in Pleroma has two unique identifiers associated:
- A webfinger `acct:` URI, used for discovery and as a verifiable global name for the user across Pleroma instances. In our example, our account's acct: URI is `acct:user@example.org`
- An author/actor URI, used in every other aspect of federation. This is the way in which users are identified in ActivityPub, the underlying protocol used for federation with other Pleroma instances.
In our case, it is `https://pleroma.example.org/users/user`.
Both account identifiers are unique and required for Pleroma. An important risk if you set up your Pleroma instance incorrectly is to create two users (with different acct: URIs) with conflicting author/actor URIs.
## WebFinger
As said earlier, each Pleroma user has an `acct`: URI, which is used for discovery and authentication. When you add @user@example.org, a webfinger query is performed. This is done in two steps:
1. Querying `https://example.org/.well-known/host-meta` (where the domain of the URL matches the domain part of the `acct`: URI) to get information on how to perform the query.
This file will indeed contain a URL template of the form `https://example.org/.well-known/webfinger?resource={uri}` that will be used in the second step.
2. Fill the returned template with the `acct`: URI to be queried and perform the query: `https://example.org/.well-known/webfinger?resource=acct:user@example.org`
## Configuring your Pleroma instance
**_DO NOT ATTEMPT TO CONFIGURE YOUR INSTANCE THIS WAY IF YOU DID NOT UNDERSTAND THE ABOVE_**
### Configuring Pleroma
Pleroma has a two configuration settings to enable using different domains for your users and Pleroma itself. `host` in `Pleroma.Web.Endpoint` and `domain` in `Pleroma.Web.WebFinger`. When the latter is not set, it defaults to the value of `host`.
*Be extra careful when configuring your Pleroma instance, as changing `host` may cause remote instances to register different accounts with the same author/actor URI, which will result in federation issues!*
```elixir
config :pleroma, Pleroma.Web.Endpoint,
url: [host: "pleroma.example.org"]
config :pleroma, Pleroma.Web.WebFinger, domain: "example.org"
```
- `domain` - is the domain for which your Pleroma instance has authority, it's the domain used in `acct:` URI. In our example, `domain` would be set to `example.org`. This is used in WebFinger account ids, which are the canonical account identifier in some other fediverse software like Mastodon. **If you change `domain`, the accounts on your server will be shown as different accounts in those software**.
- `host` - is the domain used for any URL generated for your instance, including the author/actor URL's. In our case, that would be `pleroma.example.org`. This is used in AP ids, which are the canonical account identifier in Pleroma and some other fediverse software. **You should not change this after you have set up the instance**.
### Configuring WebFinger domain
Now, you have Pleroma running at `https://pleroma.example.org` as well as a website at `https://example.org`. If you recall how webfinger queries work, the first step is to query `https://example.org/.well-known/host-meta`, which will contain an URL template.
Therefore, the easiest way to configure `example.org` is to redirect `/.well-known/host-meta` to `pleroma.example.org`.
With nginx, it would be as simple as adding:
```nginx
location = /.well-known/host-meta {
return 301 https://pleroma.example.org$request_uri;
}
```
in example.org's server block.

View File

@ -466,7 +466,7 @@
%% == PostgreSQL ==
%% {rdbms, global, default, [{workers, 10}],
%% [{server, {pgsql, "server", 5432, "database", "username", "password"}}]},
%% [{server, {pgsql, "server", "port", "database", "username", "password"}}]},
%% == ODBC (MSSQL) ==
%% {rdbms, global, default, [{workers, 10}],

View File

@ -47,7 +47,7 @@ def load_and_update_env(deleted_settings \\ [], restart_pleroma? \\ true) do
{logger, other} =
(Repo.all(ConfigDB) ++ deleted_settings)
|> Enum.map(&merge_with_default/1)
|> Enum.split_with(fn {group, _, _, _} -> group in [:logger, :quack] end)
|> Enum.split_with(fn {group, _, _, _} -> group in [:logger] end)
logger
|> Enum.sort()
@ -104,11 +104,6 @@ defp merge_with_default(%{group: group, key: key, value: value} = setting) do
end
# change logger configuration in runtime, without restart
defp configure({:quack, key, _, merged}) do
Logger.configure_backend(Quack.Logger, [{key, merged}])
:ok = update_env(:quack, key, merged)
end
defp configure({_, :backends, _, merged}) do
# removing current backends
Enum.each(Application.get_env(:logger, :backends), &Logger.remove_backend/1)

View File

@ -163,7 +163,6 @@ defp can_be_partially_updated?(%ConfigDB{} = config), do: not only_full_update?(
defp only_full_update?(%ConfigDB{group: group, key: key}) do
full_key_update = [
{:pleroma, :ecto_repos},
{:quack, :meta},
{:mime, :types},
{:cors_plug, [:max_age, :methods, :expose, :headers]},
{:swarm, :node_blacklist},
@ -386,7 +385,7 @@ defp find_valid_delimiter([delimiter | others], pattern, regex_delimiter) do
@spec module_name?(String.t()) :: boolean()
def module_name?(string) do
Regex.match?(~r/^(Pleroma|Phoenix|Tesla|Quack|Ueberauth|Swoosh)\./, string) or
Regex.match?(~r/^(Pleroma|Phoenix|Tesla|Ueberauth|Swoosh)\./, string) or
string in ["Oban", "Ueberauth", "ExSyslogger", "ConcurrentLimiter"]
end
end

View File

@ -106,5 +106,12 @@ defp adapter_middlewares(Tesla.Adapter.Gun) do
[Tesla.Middleware.FollowRedirects, Pleroma.Tesla.Middleware.ConnectionPool]
end
defp adapter_middlewares(_), do: []
defp adapter_middlewares(_) do
if Pleroma.Config.get(:env) == :test do
# Emulate redirects in test env, which are handled by adapters in other environments
[Tesla.Middleware.FollowRedirects]
else
[]
end
end
end

View File

@ -4,6 +4,7 @@
defmodule Pleroma.Object.Fetcher do
alias Pleroma.HTTP
alias Pleroma.Instances
alias Pleroma.Maps
alias Pleroma.Object
alias Pleroma.Object.Containment
@ -234,6 +235,10 @@ def fetch_and_contain_remote_object_from_id(id) when is_binary(id) do
{:ok, body} <- get_object(id),
{:ok, data} <- safe_json_decode(body),
:ok <- Containment.contain_origin_from_id(id, data) do
if not Instances.reachable?(id) do
Instances.set_reachable(id)
end
{:ok, data}
else
{:scheme, _} ->

View File

@ -1482,7 +1482,7 @@ defp normalize_image(%{"url" => url}) do
defp normalize_image(urls) when is_list(urls), do: urls |> List.first() |> normalize_image()
defp normalize_image(_), do: nil
defp object_to_user_data(data) do
defp object_to_user_data(data, additional) do
fields =
data
|> Map.get("attachment", [])
@ -1514,15 +1514,11 @@ defp object_to_user_data(data) do
public_key =
if is_map(data["publicKey"]) && is_binary(data["publicKey"]["publicKeyPem"]) do
data["publicKey"]["publicKeyPem"]
else
nil
end
shared_inbox =
if is_map(data["endpoints"]) && is_binary(data["endpoints"]["sharedInbox"]) do
data["endpoints"]["sharedInbox"]
else
nil
end
birthday =
@ -1531,13 +1527,15 @@ defp object_to_user_data(data) do
{:ok, date} -> date
{:error, _} -> nil
end
else
nil
end
show_birthday = !!birthday
user_data = %{
# if WebFinger request was already done, we probably have acct, otherwise
# we request WebFinger here
nickname = additional[:nickname_from_acct] || generate_nickname(data)
%{
ap_id: data["id"],
uri: get_actor_url(data["url"]),
ap_enabled: true,
@ -1559,23 +1557,29 @@ defp object_to_user_data(data) do
inbox: data["inbox"],
shared_inbox: shared_inbox,
accepts_chat_messages: accepts_chat_messages,
pinned_objects: pinned_objects,
birthday: birthday,
show_birthday: show_birthday
show_birthday: show_birthday,
pinned_objects: pinned_objects,
nickname: nickname
}
end
# nickname can be nil because of virtual actors
if data["preferredUsername"] do
Map.put(
user_data,
:nickname,
"#{data["preferredUsername"]}@#{URI.parse(data["id"]).host}"
)
defp generate_nickname(%{"preferredUsername" => username} = data) when is_binary(username) do
generated = "#{username}@#{URI.parse(data["id"]).host}"
if Config.get([WebFinger, :update_nickname_on_user_fetch]) do
case WebFinger.finger(generated) do
{:ok, %{"subject" => "acct:" <> acct}} -> acct
_ -> generated
end
else
Map.put(user_data, :nickname, nil)
generated
end
end
# nickname can be nil because of virtual actors
defp generate_nickname(_), do: nil
def fetch_follow_information_for_user(user) do
with {:ok, following_data} <-
Fetcher.fetch_and_contain_remote_object_from_id(user.following_address),
@ -1647,17 +1651,17 @@ defp collection_private(%{"first" => first}) do
defp collection_private(_data), do: {:ok, true}
def user_data_from_user_object(data) do
def user_data_from_user_object(data, additional \\ []) do
with {:ok, data} <- MRF.filter(data) do
{:ok, object_to_user_data(data)}
{:ok, object_to_user_data(data, additional)}
else
e -> {:error, e}
end
end
def fetch_and_prepare_user_from_ap_id(ap_id) do
def fetch_and_prepare_user_from_ap_id(ap_id, additional \\ []) do
with {:ok, data} <- Fetcher.fetch_and_contain_remote_object_from_id(ap_id),
{:ok, data} <- user_data_from_user_object(data) do
{:ok, data} <- user_data_from_user_object(data, additional) do
{:ok, maybe_update_follow_information(data)}
else
# If this has been deleted, only log a debug and not an error
@ -1735,13 +1739,13 @@ def pinned_fetch_task(%{pinned_objects: pins}) do
end
end
def make_user_from_ap_id(ap_id) do
def make_user_from_ap_id(ap_id, additional \\ []) do
user = User.get_cached_by_ap_id(ap_id)
if user && !User.ap_enabled?(user) do
Transmogrifier.upgrade_user_from_ap_id(ap_id)
else
with {:ok, data} <- fetch_and_prepare_user_from_ap_id(ap_id) do
with {:ok, data} <- fetch_and_prepare_user_from_ap_id(ap_id, additional) do
{:ok, _pid} = Task.start(fn -> pinned_fetch_task(data) end)
if user do
@ -1761,8 +1765,9 @@ def make_user_from_ap_id(ap_id) do
end
def make_user_from_nickname(nickname) do
with {:ok, %{"ap_id" => ap_id}} when not is_nil(ap_id) <- WebFinger.finger(nickname) do
make_user_from_ap_id(ap_id)
with {:ok, %{"ap_id" => ap_id, "subject" => "acct:" <> acct}} when not is_nil(ap_id) <-
WebFinger.finger(nickname) do
make_user_from_ap_id(ap_id, nickname_from_acct: acct)
else
_e -> {:error, "No AP id in WebFinger"}
end

View File

@ -131,7 +131,7 @@ def config_description do
type: {:list, :atom},
description:
"A list of actions to apply to the post. `:delist` removes the post from public timelines; " <>
"`:strip_followers` removes followers from the ActivityPub recipient list ensuring they won't be delivered to home timelines; " <>
"`:strip_followers` removes followers from the ActivityPub recipient list ensuring they won't be delivered to home timelines, additionally for followers-only it degrades to a direct message; " <>
"`:reject` rejects the message entirely",
suggestions: [:delist, :strip_followers, :reject]
}

View File

@ -282,7 +282,6 @@ def handle(%{data: %{"type" => "EmojiReact"}} = object, meta) do
# Tasks this handles:
# - Delete and unpins the create activity
# - Replace object with Tombstone
# - Set up notification
# - Reduce the user note count
# - Reduce the reply count
# - Stream out the activity
@ -324,7 +323,6 @@ def handle(%{data: %{"type" => "Delete", "object" => deleted_object}} = object,
end
if result == :ok do
Notification.create_notifications(object)
{:ok, object, meta}
else
{:error, result}

View File

@ -748,22 +748,21 @@ def get_reports(params, page, page_size) do
ActivityPub.fetch_activities([], params, :offset)
end
def update_report_state(%Activity{} = activity, state)
when state in @strip_status_report_states do
{:ok, stripped_activity} = strip_report_status_data(activity)
new_data =
activity.data
|> Map.put("state", state)
|> Map.put("object", stripped_activity.data["object"])
activity
|> Changeset.change(data: new_data)
|> Repo.update()
defp maybe_strip_report_status(data, state) do
with true <- Config.get([:instance, :report_strip_status]),
true <- state in @strip_status_report_states,
{:ok, stripped_activity} = strip_report_status_data(%Activity{data: data}) do
data |> Map.put("object", stripped_activity.data["object"])
else
_ -> data
end
end
def update_report_state(%Activity{} = activity, state) when state in @supported_report_states do
new_data = Map.put(activity.data, "state", state)
new_data =
activity.data
|> Map.put("state", state)
|> maybe_strip_report_status(state)
activity
|> Changeset.change(data: new_data)

View File

@ -4,6 +4,7 @@
defmodule Pleroma.Web.AdminAPI.Report do
alias Pleroma.Activity
alias Pleroma.Object
alias Pleroma.User
def extract_report_info(
@ -16,10 +17,42 @@ def extract_report_info(
status_ap_ids
|> Enum.reject(&is_nil(&1))
|> Enum.map(fn
act when is_map(act) -> Activity.get_by_ap_id_with_object(act["id"])
act when is_binary(act) -> Activity.get_by_ap_id_with_object(act)
act when is_map(act) ->
Activity.get_by_ap_id_with_object(act["id"]) || make_fake_activity(act, user)
act when is_binary(act) ->
Activity.get_by_ap_id_with_object(act)
end)
%{report: report, user: user, account: account, statuses: statuses}
end
defp make_fake_activity(act, user) do
%Activity{
id: "pleroma:fake",
data: %{
"actor" => user.ap_id,
"type" => "Create",
"to" => [],
"cc" => [],
"object" => act["id"],
"published" => act["published"],
"id" => act["id"],
"context" => "pleroma:fake"
},
recipients: [user.ap_id],
object: %Object{
data: %{
"actor" => user.ap_id,
"type" => "Note",
"content" => act["content"],
"published" => act["published"],
"to" => [],
"cc" => [],
"id" => act["id"],
"context" => "pleroma:fake"
}
}
}
end
end

View File

@ -47,10 +47,15 @@ def publish(%{id: "pleroma:fakeid"} = activity) do
end
@impl true
def publish(activity) do
PublisherWorker.enqueue("publish", %{"activity_id" => activity.id})
def publish(%Pleroma.Activity{data: %{"type" => type}} = activity) do
PublisherWorker.enqueue("publish", %{"activity_id" => activity.id},
priority: publish_priority(type)
)
end
defp publish_priority("Delete"), do: 3
defp publish_priority(_), do: 0
# Job Worker Callbacks
@spec perform(atom(), module(), any()) :: {:ok, any()} | {:error, any()}

View File

@ -68,7 +68,7 @@ def headers do
]
}
[{"reply-to", Jason.encode!(report_group)} | headers]
[{"report-to", Jason.encode!(report_group)} | headers]
else
headers
end

View File

@ -32,7 +32,13 @@ def host_meta do
def webfinger(resource, fmt) when fmt in ["XML", "JSON"] do
host = Pleroma.Web.Endpoint.host()
regex = ~r/(acct:)?(?<username>[a-z0-9A-Z_\.-]+)@#{host}/
regex =
if webfinger_domain = Pleroma.Config.get([__MODULE__, :domain]) do
~r/(acct:)?(?<username>[a-z0-9A-Z_\.-]+)@(#{host}|#{webfinger_domain})/
else
~r/(acct:)?(?<username>[a-z0-9A-Z_\.-]+)@#{host}/
end
with %{"username" => username} <- Regex.named_captures(regex, resource),
%User{} = user <- User.get_cached_by_nickname(username) do
@ -64,7 +70,7 @@ defp gather_aliases(%User{} = user) do
def represent_user(user, "JSON") do
%{
"subject" => "acct:#{user.nickname}@#{Pleroma.Web.Endpoint.host()}",
"subject" => "acct:#{user.nickname}@#{domain()}",
"aliases" => gather_aliases(user),
"links" => gather_links(user)
}
@ -84,12 +90,16 @@ def represent_user(user, "XML") do
:XRD,
%{xmlns: "http://docs.oasis-open.org/ns/xri/xrd-1.0"},
[
{:Subject, "acct:#{user.nickname}@#{Pleroma.Web.Endpoint.host()}"}
{:Subject, "acct:#{user.nickname}@#{domain()}"}
] ++ aliases ++ links
}
|> XmlBuilder.to_doc()
end
defp domain do
Pleroma.Config.get([__MODULE__, :domain]) || Pleroma.Web.Endpoint.host()
end
defp webfinger_from_xml(body) do
with {:ok, doc} <- XML.parse_document(body) do
subject = XML.string_from_xpath("//Subject", doc)
@ -146,17 +156,15 @@ def get_template_from_xml(body) do
end
def find_lrdd_template(domain) do
with {:ok, %{status: status, body: body}} when status in 200..299 <-
HTTP.get("http://#{domain}/.well-known/host-meta") do
# WebFinger is restricted to HTTPS - https://tools.ietf.org/html/rfc7033#section-9.1
meta_url = "https://#{domain}/.well-known/host-meta"
with {:ok, %{status: status, body: body}} when status in 200..299 <- HTTP.get(meta_url) do
get_template_from_xml(body)
else
_ ->
with {:ok, %{body: body, status: status}} when status in 200..299 <-
HTTP.get("https://#{domain}/.well-known/host-meta") do
get_template_from_xml(body)
else
e -> {:error, "Can't find LRDD template: #{inspect(e)}"}
end
error ->
Logger.warn("Can't find LRDD template in #{inspect(meta_url)}: #{inspect(error)}")
{:error, :lrdd_not_found}
end
end
@ -170,7 +178,7 @@ defp get_address_from_domain(domain, encoded_account) when is_binary(domain) do
end
end
defp get_address_from_domain(_, _), do: nil
defp get_address_from_domain(_, _), do: {:error, :webfinger_no_domain}
@spec finger(String.t()) :: {:ok, map()} | {:error, any()}
def finger(account) do
@ -187,13 +195,11 @@ def finger(account) do
encoded_account = URI.encode("acct:#{account}")
with address when is_binary(address) <- get_address_from_domain(domain, encoded_account),
response <-
{:ok, %{status: status, body: body, headers: headers}} when status in 200..299 <-
HTTP.get(
address,
[{"accept", "application/xrd+xml,application/jrd+json"}]
),
{:ok, %{status: status, body: body, headers: headers}} when status in 200..299 <-
response do
) do
case List.keyfind(headers, "content-type", 0) do
{_, content_type} ->
case Plug.Conn.Utils.media_type(content_type) do
@ -211,10 +217,9 @@ def finger(account) do
{:error, {:content_type, nil}}
end
else
e ->
Logger.debug(fn -> "Couldn't finger #{account}" end)
Logger.debug(fn -> inspect(e) end)
{:error, e}
error ->
Logger.debug("Couldn't finger #{account}: #{inspect(error)}")
error
end
end
end

View File

@ -31,6 +31,9 @@ def perform(%Job{
def perform(%Job{args: %{"op" => "cleanup_attachments", "object" => _object}}), do: {:ok, :skip}
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(900)
defp do_clean({object_ids, attachment_urls}) do
uploader = Pleroma.Config.get([Pleroma.Upload, :uploader])

View File

@ -43,4 +43,7 @@ def perform(%Job{
def perform(%Job{args: %{"op" => "delete_instance", "host" => host}}) do
Instance.perform(:delete_instance, host)
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(5)
end

View File

@ -30,6 +30,7 @@ def delete(backup) do
|> Oban.insert()
end
@impl Oban.Worker
def perform(%Job{
args: %{"op" => "process", "backup_id" => backup_id, "admin_user_id" => admin_user_id}
}) do
@ -49,6 +50,9 @@ def perform(%Job{args: %{"op" => "delete", "backup_id" => backup_id}}) do
end
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(900)
defp has_email?(user) do
not is_nil(user.email) and user.email != ""
end

View File

@ -12,4 +12,7 @@ def perform(%Job{args: %{"op" => "email", "encoded_email" => encoded_email, "con
|> :erlang.binary_to_term()
|> Pleroma.Emails.Mailer.deliver(config)
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(5)
end

View File

@ -17,4 +17,7 @@ def perform(%Job{
Pleroma.Web.CommonAPI.remove_mute(user_id, activity_id)
:ok
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(5)
end

View File

@ -19,6 +19,9 @@ def perform(%Job{args: %{"op" => "poll_end", "activity_id" => activity_id}}) do
end
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(5)
defp find_poll_activity(activity_id) do
with nil <- Activity.get_by_id(activity_id) do
{:error, :poll_activity_not_found}

View File

@ -22,4 +22,7 @@ def perform(%Job{args: %{"op" => "publish_one", "module" => module_name, "params
params = Map.new(params, fn {k, v} -> {String.to_atom(k), v} end)
Federator.perform(:publish_one, String.to_atom(module_name), params)
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(10)
end

View File

@ -35,6 +35,9 @@ def perform(%Oban.Job{args: %{"activity_id" => id}}) do
end
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(5)
defp enabled? do
with false <- Pleroma.Config.get([__MODULE__, :enabled], false) do
{:error, :expired_activities_disabled}

View File

@ -31,6 +31,9 @@ def perform(%Job{args: %{"filter_id" => id}}) do
|> Repo.delete()
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(5)
@spec get_expiration(pos_integer()) :: Job.t() | nil
def get_expiration(id) do
from(j in Job,

View File

@ -26,4 +26,7 @@ def perform(%Oban.Job{args: %{"token_id" => id, "mod" => module}}) do
|> Pleroma.Repo.get(id)
|> Pleroma.Repo.delete()
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(5)
end

View File

@ -17,4 +17,7 @@ def perform(%Job{args: %{"op" => "incoming_ap_doc", "params" => params}}) do
e -> e
end
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(5)
end

View File

@ -11,4 +11,7 @@ defmodule Pleroma.Workers.RemoteFetcherWorker do
def perform(%Job{args: %{"op" => "fetch_remote", "id" => id} = args}) do
{:ok, _object} = Fetcher.fetch_object_from_id(id, depth: args["depth"])
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(10)
end

View File

@ -37,6 +37,9 @@ def perform(%Job{args: %{"activity_id" => activity_id}}) do
end
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(5)
defp find_scheduled_activity(id) do
with nil <- Repo.get(ScheduledActivity, id) do
{:error, :scheduled_activity_not_found}

View File

@ -12,4 +12,7 @@ def perform(%Job{args: %{"op" => "user_upgrade", "user_id" => user_id}}) do
user = User.get_cached_by_id(user_id)
Pleroma.Web.ActivityPub.Transmogrifier.perform(:user_upgrade, user)
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(5)
end

View File

@ -17,4 +17,7 @@ def perform(%Job{args: %{"op" => "web_push", "notification_id" => notification_i
Pleroma.Web.Push.Impl.perform(notification)
end
@impl Oban.Worker
def timeout(_job), do: :timer.seconds(5)
end

View File

@ -13,8 +13,7 @@ def project do
start_permanent: Mix.env() == :prod,
aliases: aliases(),
deps: deps(),
test_coverage: [tool: ExCoveralls],
preferred_cli_env: ["coveralls.html": :test],
test_coverage: [tool: :covertool, summary: true],
# Docs
name: "Pleroma",
homepage_url: "https://pleroma.social/",
@ -77,7 +76,6 @@ def application do
:logger,
:runtime_tools,
:comeonin,
:quack,
:fast_sanitize,
:os_mon,
:ssl,
@ -178,7 +176,6 @@ defp deps do
branch: "no-logging"},
{:prometheus_ecto, "~> 1.4"},
{:recon, "~> 2.5"},
{:quack, "~> 0.1.1"},
{:joken, "~> 2.0"},
{:benchee, "~> 1.0"},
{:pot, "~> 1.0"},
@ -208,8 +205,7 @@ defp deps do
{:ex_machina, "~> 2.4", only: :test},
{:credo, "~> 1.4", only: [:dev, :test], runtime: false},
{:mock, "~> 0.3.5", only: :test},
# temporary downgrade for excoveralls, hackney until hackney max_connections bug will be fixed
{:excoveralls, "0.12.3", only: :test},
{:covertool, "~> 2.0", only: :test},
{:hackney, "~> 1.18.0", override: true},
{:mox, "~> 1.0", only: :test},
{:websockex, "~> 0.4.3", only: :test}

View File

@ -1,8 +1,6 @@
%{
"accept": {:hex, :accept, "0.3.5", "b33b127abca7cc948bbe6caa4c263369abf1347cfa9d8e699c6d214660f10cd1", [:rebar3], [], "hexpm", "11b18c220bcc2eab63b5470c038ef10eb6783bcb1fcdb11aa4137defa5ac1bb8"},
"base62": {:hex, :base62, "1.2.2", "85c6627eb609317b70f555294045895ffaaeb1758666ab9ef9ca38865b11e629", [:mix], [{:custom_base, "~> 0.2.1", [hex: :custom_base, repo: "hexpm", optional: false]}], "hexpm", "d41336bda8eaa5be197f1e4592400513ee60518e5b9f4dcf38f4b4dae6f377bb"},
"base64url": {:hex, :base64url, "0.0.1", "36a90125f5948e3afd7be97662a1504b934dd5dac78451ca6e9abf85a10286be", [:rebar], [], "hexpm"},
"bbcode": {:git, "https://git.pleroma.social/pleroma/elixir-libraries/bbcode.git", "f2d267675e9a7e1ad1ea9beb4cc23382762b66c2", [ref: "v0.2.0"]},
"bbcode_pleroma": {:hex, :bbcode_pleroma, "0.2.0", "d36f5bca6e2f62261c45be30fa9b92725c0655ad45c99025cb1c3e28e25803ef", [:mix], [{:nimble_parsec, "~> 0.5", [hex: :nimble_parsec, repo: "hexpm", optional: false]}], "hexpm", "19851074419a5fedb4ef49e1f01b30df504bb5dbb6d6adfc135238063bebd1c3"},
"bcrypt_elixir": {:hex, :bcrypt_elixir, "2.3.0", "6cb662d5c1b0a8858801cf20997bd006e7016aa8c52959c9ef80e0f34fb60b7a", [:make, :mix], [{:comeonin, "~> 5.3", [hex: :comeonin, repo: "hexpm", optional: false]}, {:elixir_make, "~> 0.6", [hex: :elixir_make, repo: "hexpm", optional: false]}], "hexpm", "2c81d61d4f6ed0e5cf7bf27a9109b791ff216a1034b3d541327484f46dd43769"},
"benchee": {:hex, :benchee, "1.0.1", "66b211f9bfd84bd97e6d1beaddf8fc2312aaabe192f776e8931cb0c16f53a521", [:mix], [{:deep_merge, "~> 1.0", [hex: :deep_merge, repo: "hexpm", optional: false]}], "hexpm", "3ad58ae787e9c7c94dd7ceda3b587ec2c64604563e049b2a0e8baafae832addb"},
@ -17,11 +15,11 @@
"concurrent_limiter": {:hex, :concurrent_limiter, "0.1.1", "43ae1dc23edda1ab03dd66febc739c4ff710d047bb4d735754909f9a474ae01c", [:mix], [{:telemetry, "~> 0.3", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "53968ff238c0fbb4d7ed76ddb1af0be6f3b2f77909f6796e249e737c505a16eb"},
"connection": {:hex, :connection, "1.1.0", "ff2a49c4b75b6fb3e674bfc5536451607270aac754ffd1bdfe175abe4a6d7a68", [:mix], [], "hexpm", "722c1eb0a418fbe91ba7bd59a47e28008a189d47e37e0e7bb85585a016b2869c"},
"cors_plug": {:hex, :cors_plug, "2.0.3", "316f806d10316e6d10f09473f19052d20ba0a0ce2a1d910ddf57d663dac402ae", [:mix], [{:plug, "~> 1.8", [hex: :plug, repo: "hexpm", optional: false]}], "hexpm", "ee4ae1418e6ce117fc42c2ba3e6cbdca4e95ecd2fe59a05ec6884ca16d469aea"},
"covertool": {:hex, :covertool, "2.0.4", "54acff6cddd88d28dea663cd2e1fe20dd32fcf5f5d3aff7d59031ce44ce39efa", [:rebar3], [], "hexpm", "5c9568ba4308fda2082172737c80c31d991ea83961eb10791f06106a870d0cdc"},
"cowboy": {:hex, :cowboy, "2.9.0", "865dd8b6607e14cf03282e10e934023a1bd8be6f6bacf921a7e2a96d800cd452", [:make, :rebar3], [{:cowlib, "2.11.0", [hex: :cowlib, repo: "hexpm", optional: false]}, {:ranch, "1.8.0", [hex: :ranch, repo: "hexpm", optional: false]}], "hexpm", "2c729f934b4e1aa149aff882f57c6372c15399a20d54f65c8d67bef583021bde"},
"cowboy_telemetry": {:hex, :cowboy_telemetry, "0.3.1", "ebd1a1d7aff97f27c66654e78ece187abdc646992714164380d8a041eda16754", [:rebar3], [{:cowboy, "~> 2.7", [hex: :cowboy, repo: "hexpm", optional: false]}, {:telemetry, "~> 0.4", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "3a6efd3366130eab84ca372cbd4a7d3c3a97bdfcfb4911233b035d117063f0af"},
"cowlib": {:hex, :cowlib, "2.11.0", "0b9ff9c346629256c42ebe1eeb769a83c6cb771a6ee5960bd110ab0b9b872063", [:make, :rebar3], [], "hexpm", "2b3e9da0b21c4565751a6d4901c20d1b4cc25cbb7fd50d91d2ab6dd287bc86a9"},
"credo": {:hex, :credo, "1.5.5", "e8f422026f553bc3bebb81c8e8bf1932f498ca03339856c7fec63d3faac8424b", [:mix], [{:bunt, "~> 0.2.0", [hex: :bunt, repo: "hexpm", optional: false]}, {:file_system, "~> 0.2.8", [hex: :file_system, repo: "hexpm", optional: false]}, {:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: false]}], "hexpm", "dd8623ab7091956a855dc9f3062486add9c52d310dfd62748779c4315d8247de"},
"crontab": {:hex, :crontab, "1.1.8", "2ce0e74777dfcadb28a1debbea707e58b879e6aa0ffbf9c9bb540887bce43617", [:mix], [{:ecto, "~> 1.0 or ~> 2.0 or ~> 3.0", [hex: :ecto, repo: "hexpm", optional: true]}], "hexpm"},
"crypt": {:git, "https://github.com/msantos/crypt.git", "f75cd55325e33cbea198fb41fe41871392f8fb76", [ref: "f75cd55325e33cbea198fb41fe41871392f8fb76"]},
"custom_base": {:hex, :custom_base, "0.2.1", "4a832a42ea0552299d81652aa0b1f775d462175293e99dfbe4d7dbaab785a706", [:mix], [], "hexpm", "8df019facc5ec9603e94f7270f1ac73ddf339f56ade76a721eaa57c1493ba463"},
"db_connection": {:hex, :db_connection, "2.4.0", "d04b1b73795dae60cead94189f1b8a51cc9e1f911c234cc23074017c43c031e5", [:mix], [{:connection, "~> 1.0", [hex: :connection, repo: "hexpm", optional: false]}, {:telemetry, "~> 0.4 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "ad416c21ad9f61b3103d254a71b63696ecadb6a917b36f563921e0de00d7d7c8"},
@ -34,18 +32,15 @@
"ecto_enum": {:hex, :ecto_enum, "1.4.0", "d14b00e04b974afc69c251632d1e49594d899067ee2b376277efd8233027aec8", [:mix], [{:ecto, ">= 3.0.0", [hex: :ecto, repo: "hexpm", optional: false]}, {:ecto_sql, "> 3.0.0", [hex: :ecto_sql, repo: "hexpm", optional: false]}, {:mariaex, ">= 0.0.0", [hex: :mariaex, repo: "hexpm", optional: true]}, {:postgrex, ">= 0.0.0", [hex: :postgrex, repo: "hexpm", optional: true]}], "hexpm", "8fb55c087181c2b15eee406519dc22578fa60dd82c088be376d0010172764ee4"},
"ecto_psql_extras": {:hex, :ecto_psql_extras, "0.7.4", "5d43fd088d39a158c860b17e8d210669587f63ec89ea122a4654861c8c6e2db4", [:mix], [{:ecto_sql, "~> 3.4", [hex: :ecto_sql, repo: "hexpm", optional: false]}, {:postgrex, ">= 0.15.7", [hex: :postgrex, repo: "hexpm", optional: false]}, {:table_rex, "~> 3.1.1", [hex: :table_rex, repo: "hexpm", optional: false]}], "hexpm", "311db02f1b772e3d0dc7f56a05044b5e1499d78ed6abf38885e1ca70059449e5"},
"ecto_sql": {:hex, :ecto_sql, "3.6.2", "9526b5f691701a5181427634c30655ac33d11e17e4069eff3ae1176c764e0ba3", [:mix], [{:db_connection, "~> 2.2", [hex: :db_connection, repo: "hexpm", optional: false]}, {:ecto, "~> 3.6.2", [hex: :ecto, repo: "hexpm", optional: false]}, {:myxql, "~> 0.4.0 or ~> 0.5.0", [hex: :myxql, repo: "hexpm", optional: true]}, {:postgrex, "~> 0.15.0 or ~> 1.0", [hex: :postgrex, repo: "hexpm", optional: true]}, {:tds, "~> 2.1.1", [hex: :tds, repo: "hexpm", optional: true]}, {:telemetry, "~> 0.4.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "5ec9d7e6f742ea39b63aceaea9ac1d1773d574ea40df5a53ef8afbd9242fdb6b"},
"eimp": {:hex, :eimp, "1.0.14", "fc297f0c7e2700457a95a60c7010a5f1dcb768a083b6d53f49cd94ab95a28f22", [:rebar3], [{:p1_utils, "1.0.18", [hex: :p1_utils, repo: "hexpm", optional: false]}], "hexpm", "501133f3112079b92d9e22da8b88bf4f0e13d4d67ae9c15c42c30bd25ceb83b6"},
"elixir_make": {:hex, :elixir_make, "0.6.2", "7dffacd77dec4c37b39af867cedaabb0b59f6a871f89722c25b28fcd4bd70530", [:mix], [], "hexpm", "03e49eadda22526a7e5279d53321d1cced6552f344ba4e03e619063de75348d9"},
"esshd": {:hex, :esshd, "0.1.1", "d4dd4c46698093a40a56afecce8a46e246eb35463c457c246dacba2e056f31b5", [:mix], [], "hexpm", "d73e341e3009d390aa36387dc8862860bf9f874c94d9fd92ade2926376f49981"},
"eternal": {:hex, :eternal, "1.2.2", "d1641c86368de99375b98d183042dd6c2b234262b8d08dfd72b9eeaafc2a1abd", [:mix], [], "hexpm", "2c9fe32b9c3726703ba5e1d43a1d255a4f3f2d8f8f9bc19f094c7cb1a7a9e782"},
"ex2ms": {:hex, :ex2ms, "1.5.0", "19e27f9212be9a96093fed8cdfbef0a2b56c21237196d26760f11dfcfae58e97", [:mix], [], "hexpm"},
"ex_aws": {:hex, :ex_aws, "2.1.9", "dc4865ecc20a05190a34a0ac5213e3e5e2b0a75a0c2835e923ae7bfeac5e3c31", [:mix], [{:configparser_ex, "~> 4.0", [hex: :configparser_ex, repo: "hexpm", optional: true]}, {:hackney, "~> 1.9", [hex: :hackney, repo: "hexpm", optional: true]}, {:jason, "~> 1.1", [hex: :jason, repo: "hexpm", optional: true]}, {:jsx, "~> 3.0", [hex: :jsx, repo: "hexpm", optional: true]}, {:sweet_xml, "~> 0.6", [hex: :sweet_xml, repo: "hexpm", optional: true]}], "hexpm", "3e6c776703c9076001fbe1f7c049535f042cb2afa0d2cbd3b47cbc4e92ac0d10"},
"ex_aws_s3": {:hex, :ex_aws_s3, "2.2.0", "07a09de557070320e264893c0acc8a1d2e7ddf80155736e0aed966486d1988e6", [:mix], [{:ex_aws, "~> 2.0", [hex: :ex_aws, repo: "hexpm", optional: false]}, {:sweet_xml, ">= 0.0.0", [hex: :sweet_xml, repo: "hexpm", optional: true]}], "hexpm", "15175c613371e29e1f88b78ec8a4327389ca1ec5b34489744b175727496b21bd"},
"ex_const": {:hex, :ex_const, "0.2.4", "d06e540c9d834865b012a17407761455efa71d0ce91e5831e86881b9c9d82448", [:mix], [], "hexpm", "96fd346610cc992b8f896ed26a98be82ac4efb065a0578f334a32d60a3ba9767"},
"ex_doc": {:hex, :ex_doc, "0.24.2", "e4c26603830c1a2286dae45f4412a4d1980e1e89dc779fcd0181ed1d5a05c8d9", [:mix], [{:earmark_parser, "~> 1.4.0", [hex: :earmark_parser, repo: "hexpm", optional: false]}, {:makeup_elixir, "~> 0.14", [hex: :makeup_elixir, repo: "hexpm", optional: false]}, {:makeup_erlang, "~> 0.1", [hex: :makeup_erlang, repo: "hexpm", optional: false]}], "hexpm", "e134e1d9e821b8d9e4244687fb2ace58d479b67b282de5158333b0d57c6fb7da"},
"ex_machina": {:hex, :ex_machina, "2.7.0", "b792cc3127fd0680fecdb6299235b4727a4944a09ff0fa904cc639272cd92dc7", [:mix], [{:ecto, "~> 2.2 or ~> 3.0", [hex: :ecto, repo: "hexpm", optional: true]}, {:ecto_sql, "~> 3.0", [hex: :ecto_sql, repo: "hexpm", optional: true]}], "hexpm", "419aa7a39bde11894c87a615c4ecaa52d8f107bbdd81d810465186f783245bf8"},
"ex_syslogger": {:hex, :ex_syslogger, "1.5.2", "72b6aa2d47a236e999171f2e1ec18698740f40af0bd02c8c650bf5f1fd1bac79", [:mix], [{:poison, ">= 1.5.0", [hex: :poison, repo: "hexpm", optional: true]}, {:syslog, "~> 1.1.0", [hex: :syslog, repo: "hexpm", optional: false]}], "hexpm", "ab9fab4136dbc62651ec6f16fa4842f10cf02ab4433fa3d0976c01be99398399"},
"excoveralls": {:hex, :excoveralls, "0.12.3", "2142be7cb978a3ae78385487edda6d1aff0e482ffc6123877bb7270a8ffbcfe0", [:mix], [{:hackney, "~> 1.0", [hex: :hackney, repo: "hexpm", optional: false]}, {:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: false]}], "hexpm", "568a3e616c264283f5dea5b020783ae40eef3f7ee2163f7a67cbd7b35bcadada"},
"fast_html": {:hex, :fast_html, "2.0.5", "c61760340606c1077ff1f196f17834056cb1dd3d5cb92a9f2cabf28bc6221c3c", [:make, :mix], [{:elixir_make, "~> 0.4", [hex: :elixir_make, repo: "hexpm", optional: false]}, {:nimble_pool, "~> 0.2.0", [hex: :nimble_pool, repo: "hexpm", optional: false]}], "hexpm", "605f4f4829443c14127694ebabb681778712ceecb4470ec32aa31012330e6506"},
"fast_sanitize": {:hex, :fast_sanitize, "0.2.2", "3cbbaebaea6043865dfb5b4ecb0f1af066ad410a51470e353714b10c42007b81", [:mix], [{:fast_html, "~> 2.0", [hex: :fast_html, repo: "hexpm", optional: false]}, {:plug, "~> 1.8", [hex: :plug, repo: "hexpm", optional: false]}], "hexpm", "69f204db9250afa94a0d559d9110139850f57de2b081719fbafa1e9a89e94466"},
"file_system": {:hex, :file_system, "0.2.10", "fb082005a9cd1711c05b5248710f8826b02d7d1784e7c3451f9c1231d4fc162d", [:mix], [], "hexpm", "41195edbfb562a593726eda3b3e8b103a309b733ad25f3d642ba49696bf715dc"},
@ -53,13 +48,10 @@
"flake_id": {:hex, :flake_id, "0.1.0", "7716b086d2e405d09b647121a166498a0d93d1a623bead243e1f74216079ccb3", [:mix], [{:base62, "~> 1.2", [hex: :base62, repo: "hexpm", optional: false]}, {:ecto, ">= 2.0.0", [hex: :ecto, repo: "hexpm", optional: true]}], "hexpm", "31fc8090fde1acd267c07c36ea7365b8604055f897d3a53dd967658c691bd827"},
"floki": {:hex, :floki, "0.30.1", "75d35526d3a1459920b6e87fdbc2e0b8a3670f965dd0903708d2b267e0904c55", [:mix], [{:html_entities, "~> 0.5.0", [hex: :html_entities, repo: "hexpm", optional: false]}], "hexpm", "e9c03524447d1c4cbfccd672d739b8c18453eee377846b119d4fd71b1a176bb8"},
"gen_smtp": {:hex, :gen_smtp, "0.15.0", "9f51960c17769b26833b50df0b96123605a8024738b62db747fece14eb2fbfcc", [:rebar3], [], "hexpm", "29bd14a88030980849c7ed2447b8db6d6c9278a28b11a44cafe41b791205440f"},
"gen_stage": {:hex, :gen_stage, "0.14.3", "d0c66f1c87faa301c1a85a809a3ee9097a4264b2edf7644bf5c123237ef732bf", [:mix], [], "hexpm"},
"gen_state_machine": {:hex, :gen_state_machine, "2.0.5", "9ac15ec6e66acac994cc442dcc2c6f9796cf380ec4b08267223014be1c728a95", [:mix], [], "hexpm"},
"gettext": {:git, "https://github.com/tusooa/gettext.git", "72fb2496b6c5280ed911bdc3756890e7f38a4808", [ref: "72fb2496b6c5280ed911bdc3756890e7f38a4808"]},
"gun": {:hex, :gun, "2.0.0-rc.2", "7c489a32dedccb77b6e82d1f3c5a7dadfbfa004ec14e322cdb5e579c438632d2", [:make, :rebar3], [{:cowlib, "2.11.0", [hex: :cowlib, repo: "hexpm", optional: false]}], "hexpm", "6b9d1eae146410d727140dbf8b404b9631302ecc2066d1d12f22097ad7d254fc"},
"hackney": {:hex, :hackney, "1.18.0", "c4443d960bb9fba6d01161d01cd81173089686717d9490e5d3606644c48d121f", [:rebar3], [{:certifi, "~>2.8.0", [hex: :certifi, repo: "hexpm", optional: false]}, {:idna, "~>6.1.0", [hex: :idna, repo: "hexpm", optional: false]}, {:metrics, "~>1.0.0", [hex: :metrics, repo: "hexpm", optional: false]}, {:mimerl, "~>1.1", [hex: :mimerl, repo: "hexpm", optional: false]}, {:parse_trans, "3.3.1", [hex: :parse_trans, repo: "hexpm", optional: false]}, {:ssl_verify_fun, "~>1.1.0", [hex: :ssl_verify_fun, repo: "hexpm", optional: false]}, {:unicode_util_compat, "~>0.7.0", [hex: :unicode_util_compat, repo: "hexpm", optional: false]}], "hexpm", "9afcda620704d720db8c6a3123e9848d09c87586dc1c10479c42627b905b5c5e"},
"html_entities": {:hex, :html_entities, "0.5.2", "9e47e70598da7de2a9ff6af8758399251db6dbb7eebe2b013f2bbd2515895c3c", [:mix], [], "hexpm", "c53ba390403485615623b9531e97696f076ed415e8d8058b1dbaa28181f4fdcc"},
"html_sanitize_ex": {:hex, :html_sanitize_ex, "1.3.0", "f005ad692b717691203f940c686208aa3d8ffd9dd4bb3699240096a51fa9564e", [:mix], [{:mochiweb, "~> 2.15", [hex: :mochiweb, repo: "hexpm", optional: false]}], "hexpm"},
"http_signatures": {:hex, :http_signatures, "0.1.1", "ca7ebc1b61542b163644c8c3b1f0e0f41037d35f2395940d3c6c7deceab41fd8", [:mix], [], "hexpm", "cc3b8a007322cc7b624c0c15eec49ee58ac977254ff529a3c482f681465942a3"},
"httpoison": {:hex, :httpoison, "1.8.0", "6b85dea15820b7804ef607ff78406ab449dd78bed923a49c7160e1886e987a3d", [:mix], [{:hackney, "~> 1.17", [hex: :hackney, repo: "hexpm", optional: false]}], "hexpm", "28089eaa98cf90c66265b6b5ad87c59a3729bea2e74e9d08f9b51eb9729b3c3a"},
"idna": {:hex, :idna, "6.1.1", "8a63070e9f7d0c62eb9d9fcb360a7de382448200fbbd1b106cc96d3d8099df8d", [:rebar3], [{:unicode_util_compat, "~>0.7.0", [hex: :unicode_util_compat, repo: "hexpm", optional: false]}], "hexpm", "92376eb7894412ed19ac475e4a86f7b413c1b9fbb5bd16dccd57934157944cea"},
@ -68,7 +60,6 @@
"joken": {:hex, :joken, "2.3.0", "62a979c46f2c81dcb8ddc9150453b60d3757d1ac393c72bb20fc50a7b0827dc6", [:mix], [{:jose, "~> 1.10", [hex: :jose, repo: "hexpm", optional: false]}], "hexpm", "57b263a79c0ec5d536ac02d569c01e6b4de91bd1cb825625fe90eab4feb7bc1e"},
"jose": {:hex, :jose, "1.11.1", "59da64010c69aad6cde2f5b9248b896b84472e99bd18f246085b7b9fe435dcdb", [:mix, :rebar3], [], "hexpm", "078f6c9fb3cd2f4cfafc972c814261a7d1e8d2b3685c0a76eb87e158efff1ac5"},
"jumper": {:hex, :jumper, "1.0.1", "3c00542ef1a83532b72269fab9f0f0c82bf23a35e27d278bfd9ed0865cecabff", [:mix], [], "hexpm", "318c59078ac220e966d27af3646026db9b5a5e6703cb2aa3e26bcfaba65b7433"},
"libring": {:hex, :libring, "1.4.0", "41246ba2f3fbc76b3971f6bce83119dfec1eee17e977a48d8a9cfaaf58c2a8d6", [:mix], [], "hexpm"},
"linkify": {:hex, :linkify, "0.5.2", "fb66be139fdf1656ecb31f78a93592724d1b78d960a1b3598bd661013ea0e3c7", [:mix], [], "hexpm", "8d71ac690218d8952c90cbeb63cb8cc33738bb230d8a56d487d9447f2a5eab86"},
"majic": {:hex, :majic, "1.0.0", "37e50648db5f5c2ff0c9fb46454d034d11596c03683807b9fb3850676ffdaab3", [:make, :mix], [{:elixir_make, "~> 0.6.1", [hex: :elixir_make, repo: "hexpm", optional: false]}, {:mime, "~> 1.0", [hex: :mime, repo: "hexpm", optional: false]}, {:nimble_pool, "~> 0.2", [hex: :nimble_pool, repo: "hexpm", optional: false]}, {:plug, "~> 1.0", [hex: :plug, repo: "hexpm", optional: true]}], "hexpm", "7905858f76650d49695f14ea55cd9aaaee0c6654fa391671d4cf305c275a0a9e"},
"makeup": {:hex, :makeup, "1.0.5", "d5a830bc42c9800ce07dd97fa94669dfb93d3bf5fcf6ea7a0c67b2e0e4a7f26c", [:mix], [{:nimble_parsec, "~> 0.5 or ~> 1.0", [hex: :nimble_parsec, repo: "hexpm", optional: false]}], "hexpm", "cfa158c02d3f5c0c665d0af11512fed3fba0144cf1aadee0f2ce17747fba2ca9"},
@ -79,20 +70,15 @@
"mime": {:hex, :mime, "1.6.0", "dabde576a497cef4bbdd60aceee8160e02a6c89250d6c0b29e56c0dfb00db3d2", [:mix], [], "hexpm", "31a1a8613f8321143dde1dafc36006a17d28d02bdfecb9e95a880fa7aabd19a7"},
"mimerl": {:hex, :mimerl, "1.2.0", "67e2d3f571088d5cfd3e550c383094b47159f3eee8ffa08e64106cdf5e981be3", [:rebar3], [], "hexpm", "f278585650aa581986264638ebf698f8bb19df297f66ad91b18910dfc6e19323"},
"mint": {:hex, :mint, "1.4.0", "cd7d2451b201fc8e4a8fd86257fb3878d9e3752899eb67b0c5b25b180bde1212", [:mix], [{:castore, "~> 0.1.0", [hex: :castore, repo: "hexpm", optional: true]}], "hexpm", "10a99e144b815cbf8522dccbc8199d15802440fc7a64d67b6853adb6fa170217"},
"mochiweb": {:hex, :mochiweb, "2.18.0", "eb55f1db3e6e960fac4e6db4e2db9ec3602cc9f30b86cd1481d56545c3145d2e", [:rebar3], [], "hexpm"},
"mock": {:hex, :mock, "0.3.7", "75b3bbf1466d7e486ea2052a73c6e062c6256fb429d6797999ab02fa32f29e03", [:mix], [{:meck, "~> 0.9.2", [hex: :meck, repo: "hexpm", optional: false]}], "hexpm", "4da49a4609e41fd99b7836945c26f373623ea968cfb6282742bcb94440cf7e5c"},
"mogrify": {:hex, :mogrify, "0.9.1", "a26f107c4987477769f272bd0f7e3ac4b7b75b11ba597fd001b877beffa9c068", [:mix], [], "hexpm", "134edf189337d2125c0948bf0c228fdeef975c594317452d536224069a5b7f05"},
"mox": {:hex, :mox, "1.0.0", "4b3c7005173f47ff30641ba044eb0fe67287743eec9bd9545e37f3002b0a9f8b", [:mix], [], "hexpm", "201b0a20b7abdaaab083e9cf97884950f8a30a1350a1da403b3145e213c6f4df"},
"myhtmlex": {:git, "https://git.pleroma.social/pleroma/myhtmlex.git", "ad0097e2f61d4953bfef20fb6abddf23b87111e6", [ref: "ad0097e2f61d4953bfef20fb6abddf23b87111e6", submodules: true]},
"nimble_options": {:hex, :nimble_options, "0.4.0", "c89babbab52221a24b8d1ff9e7d838be70f0d871be823165c94dd3418eea728f", [:mix], [], "hexpm", "e6701c1af326a11eea9634a3b1c62b475339ace9456c1a23ec3bc9a847bca02d"},
"nimble_parsec": {:hex, :nimble_parsec, "0.5.0", "90e2eca3d0266e5c53f8fbe0079694740b9c91b6747f2b7e3c5d21966bba8300", [:mix], [], "hexpm", "5c040b8469c1ff1b10093d3186e2e10dbe483cd73d79ec017993fb3985b8a9b3"},
"nimble_pool": {:hex, :nimble_pool, "0.2.4", "1db8e9f8a53d967d595e0b32a17030cdb6c0dc4a451b8ac787bf601d3f7704c3", [:mix], [], "hexpm", "367e8071e137b787764e6a9992ccb57b276dc2282535f767a07d881951ebeac6"},
"nodex": {:git, "https://git.pleroma.social/pleroma/nodex", "cb6730f943cfc6aad674c92161be23a8411f15d1", [ref: "cb6730f943cfc6aad674c92161be23a8411f15d1"]},
"oban": {:hex, :oban, "2.3.4", "ec7509b9af2524d55f529cb7aee93d36131ae0bf0f37706f65d2fe707f4d9fd8", [:mix], [{:ecto_sql, ">= 3.4.3", [hex: :ecto_sql, repo: "hexpm", optional: false]}, {:jason, "~> 1.1", [hex: :jason, repo: "hexpm", optional: false]}, {:postgrex, "~> 0.14", [hex: :postgrex, repo: "hexpm", optional: false]}, {:telemetry, "~> 0.4", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "c70ca0434758fd1805422ea4446af5e910ddc697c0c861549c8f0eb0cfbd2fdf"},
"open_api_spex": {:hex, :open_api_spex, "3.10.0", "94e9521ad525b3fcf6dc77da7c45f87fdac24756d4de588cb0816b413e7c1844", [:mix], [{:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: true]}, {:plug, "~> 1.7", [hex: :plug, repo: "hexpm", optional: false]}, {:poison, "~> 3.1", [hex: :poison, repo: "hexpm", optional: true]}], "hexpm", "2dbb2bde3d2b821f06936e8dfaf3284331186556291946d84eeba3750ac28765"},
"p1_utils": {:hex, :p1_utils, "1.0.18", "3fe224de5b2e190d730a3c5da9d6e8540c96484cf4b4692921d1e28f0c32b01c", [:rebar3], [], "hexpm", "1fc8773a71a15553b179c986b22fbeead19b28fe486c332d4929700ffeb71f88"},
"parse_trans": {:hex, :parse_trans, "3.3.1", "16328ab840cc09919bd10dab29e431da3af9e9e7e7e6f0089dd5a2d2820011d8", [:rebar3], [], "hexpm", "07cd9577885f56362d414e8c4c4e6bdf10d43a8767abb92d24cbe8b24c54888b"},
"pbkdf2_elixir": {:hex, :pbkdf2_elixir, "1.2.1", "9cbe354b58121075bd20eb83076900a3832324b7dd171a6895fab57b6bb2752c", [:mix], [{:comeonin, "~> 5.3", [hex: :comeonin, repo: "hexpm", optional: false]}], "hexpm", "d3b40a4a4630f0b442f19eca891fcfeeee4c40871936fed2f68e1c4faa30481f"},
"phoenix": {:hex, :phoenix, "1.5.9", "a6368d36cfd59d917b37c44386e01315bc89f7609a10a45a22f47c007edf2597", [:mix], [{:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: true]}, {:phoenix_html, "~> 2.13 or ~> 3.0", [hex: :phoenix_html, repo: "hexpm", optional: true]}, {:phoenix_pubsub, "~> 2.0", [hex: :phoenix_pubsub, repo: "hexpm", optional: false]}, {:plug, "~> 1.10", [hex: :plug, repo: "hexpm", optional: false]}, {:plug_cowboy, "~> 1.0 or ~> 2.2", [hex: :plug_cowboy, repo: "hexpm", optional: true]}, {:plug_crypto, "~> 1.1.2 or ~> 1.2", [hex: :plug_crypto, repo: "hexpm", optional: false]}, {:telemetry, "~> 0.4", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "7e4bce20a67c012f1fbb0af90e5da49fa7bf0d34e3a067795703b74aef75427d"},
"phoenix_ecto": {:hex, :phoenix_ecto, "4.2.1", "13f124cf0a3ce0f1948cf24654c7b9f2347169ff75c1123f44674afee6af3b03", [:mix], [{:ecto, "~> 3.0", [hex: :ecto, repo: "hexpm", optional: false]}, {:phoenix_html, "~> 2.14.2 or ~> 2.15", [hex: :phoenix_html, repo: "hexpm", optional: true]}, {:plug, "~> 1.0", [hex: :plug, repo: "hexpm", optional: false]}], "hexpm", "478a1bae899cac0a6e02be1deec7e2944b7754c04e7d4107fc5a517f877743c0"},
"phoenix_html": {:hex, :phoenix_html, "3.1.0", "0b499df05aad27160d697a9362f0e89fa0e24d3c7a9065c2bd9d38b4d1416c09", [:mix], [{:plug, "~> 1.5", [hex: :plug, repo: "hexpm", optional: true]}], "hexpm", "0c0a98a2cefa63433657983a2a594c7dee5927e4391e0f1bfd3a151d1def33fc"},
@ -114,7 +100,6 @@
"prometheus_phoenix": {:hex, :prometheus_phoenix, "1.3.0", "c4b527e0b3a9ef1af26bdcfbfad3998f37795b9185d475ca610fe4388fdd3bb5", [:mix], [{:phoenix, "~> 1.4", [hex: :phoenix, repo: "hexpm", optional: false]}, {:prometheus_ex, "~> 1.3 or ~> 2.0 or ~> 3.0", [hex: :prometheus_ex, repo: "hexpm", optional: false]}], "hexpm", "c4d1404ac4e9d3d963da601db2a7d8ea31194f0017057fabf0cfb9bf5a6c8c75"},
"prometheus_phx": {:git, "https://git.pleroma.social/pleroma/elixir-libraries/prometheus-phx.git", "9cd8f248c9381ffedc799905050abce194a97514", [branch: "no-logging"]},
"prometheus_plugs": {:hex, :prometheus_plugs, "1.1.5", "25933d48f8af3a5941dd7b621c889749894d8a1082a6ff7c67cc99dec26377c5", [:mix], [{:accept, "~> 0.1", [hex: :accept, repo: "hexpm", optional: false]}, {:plug, "~> 1.0", [hex: :plug, repo: "hexpm", optional: false]}, {:prometheus_ex, "~> 1.1 or ~> 2.0 or ~> 3.0", [hex: :prometheus_ex, repo: "hexpm", optional: false]}, {:prometheus_process_collector, "~> 1.1", [hex: :prometheus_process_collector, repo: "hexpm", optional: true]}], "hexpm", "0273a6483ccb936d79ca19b0ab629aef0dba958697c94782bb728b920dfc6a79"},
"quack": {:hex, :quack, "0.1.1", "cca7b4da1a233757fdb44b3334fce80c94785b3ad5a602053b7a002b5a8967bf", [:mix], [{:poison, ">= 1.0.0", [hex: :poison, repo: "hexpm", optional: false]}, {:tesla, "~> 1.2.0", [hex: :tesla, repo: "hexpm", optional: false]}], "hexpm", "d736bfa7444112eb840027bb887832a0e403a4a3437f48028c3b29a2dbbd2543"},
"ranch": {:hex, :ranch, "1.8.0", "8c7a100a139fd57f17327b6413e4167ac559fbc04ca7448e9be9057311597a1d", [:make, :rebar3], [], "hexpm", "49fbcfd3682fab1f5d109351b61257676da1a2fdbe295904176d5e521a2ddfe5"},
"recon": {:hex, :recon, "2.5.1", "430ffa60685ac1efdfb1fe4c97b8767c92d0d92e6e7c3e8621559ba77598678a", [:mix, :rebar3], [], "hexpm", "5721c6b6d50122d8f68cccac712caa1231f97894bab779eff5ff0f886cb44648"},
"remote_ip": {:git, "https://git.pleroma.social/pleroma/remote_ip.git", "b647d0deecaa3acb140854fe4bda5b7e1dc6d1c8", [ref: "b647d0deecaa3acb140854fe4bda5b7e1dc6d1c8"]},

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,197 @@
msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2022-09-18 19:11+0300\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: Automatically generated\n"
"Language-Team: none\n"
"Language: uk\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"X-Generator: Translate Toolkit 3.7.2\n"
## This file is a PO Template file.
##
## "msgid"s here are often extracted from source code.
## Add new translations manually only if they're dynamic
## translations that can't be statically extracted.
##
## Run "mix gettext.extract" to bring this file up to
## date. Leave "msgstr"s empty as changing them here as no
## effect: edit them in PO (.po) files instead.
#: lib/pleroma/web/api_spec/render_error.ex:122
#, elixir-autogen, elixir-format
msgid "%{name} - %{count} is not a multiple of %{multiple}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:131
#, elixir-autogen, elixir-format
msgid "%{name} - %{value} is larger than exclusive maximum %{max}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:140
#, elixir-autogen, elixir-format
msgid "%{name} - %{value} is larger than inclusive maximum %{max}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:149
#, elixir-autogen, elixir-format
msgid "%{name} - %{value} is smaller than exclusive minimum %{min}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:158
#, elixir-autogen, elixir-format
msgid "%{name} - %{value} is smaller than inclusive minimum %{min}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:102
#, elixir-autogen, elixir-format
msgid "%{name} - Array items must be unique."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:114
#, elixir-autogen, elixir-format
msgid "%{name} - Array length %{length} is larger than maxItems: %{}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:106
#, elixir-autogen, elixir-format
msgid "%{name} - Array length %{length} is smaller than minItems: %{min}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:166
#, elixir-autogen, elixir-format
msgid "%{name} - Invalid %{type}. Got: %{value}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:174
#, elixir-autogen, elixir-format
msgid "%{name} - Invalid format. Expected %{format}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:51
#, elixir-autogen, elixir-format
msgid "%{name} - Invalid schema.type. Got: %{type}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:178
#, elixir-autogen, elixir-format
msgid "%{name} - Invalid value for enum."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:95
#, elixir-autogen, elixir-format
msgid "%{name} - String length is larger than maxLength: %{length}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:88
#, elixir-autogen, elixir-format
msgid "%{name} - String length is smaller than minLength: %{length}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:63
#, elixir-autogen, elixir-format
msgid "%{name} - null value where %{type} expected."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:60
#, elixir-autogen, elixir-format
msgid "%{name} - null value."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:182
#, elixir-autogen, elixir-format
msgid "Failed to cast to any schema in %{polymorphic_type}"
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:71
#, elixir-autogen, elixir-format
msgid "Failed to cast value as %{invalid_schema}. Value must be castable using `allOf` schemas listed."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:84
#, elixir-autogen, elixir-format
msgid "Failed to cast value to one of: %{failed_schemas}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:78
#, elixir-autogen, elixir-format
msgid "Failed to cast value using any of: %{failed_schemas}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:212
#, elixir-autogen, elixir-format
msgid "Invalid value for header: %{name}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:204
#, elixir-autogen, elixir-format
msgid "Missing field: %{name}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:208
#, elixir-autogen, elixir-format
msgid "Missing header: %{name}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:196
#, elixir-autogen, elixir-format
msgid "No value provided for required discriminator `%{field}`."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:216
#, elixir-autogen, elixir-format
msgid "Object property count %{property_count} is greater than maxProperties: %{max_properties}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:224
#, elixir-autogen, elixir-format
msgid "Object property count %{property_count} is less than minProperties: %{min_properties}"
msgstr ""
#: lib/pleroma/web/templates/static_fe/static_fe/error.html.eex:2
#, elixir-autogen, elixir-format
msgid "Oops"
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:188
#, elixir-autogen, elixir-format
msgid "Unexpected field: %{name}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:200
#, elixir-autogen, elixir-format
msgid "Unknown schema: %{name}."
msgstr ""
#: lib/pleroma/web/api_spec/render_error.ex:192
#, elixir-autogen, elixir-format
msgid "Value used as discriminator for `%{field}` matches no schemas."
msgstr ""
#: lib/pleroma/web/templates/embed/show.html.eex:43
#: lib/pleroma/web/templates/static_fe/static_fe/_notice.html.eex:37
#, elixir-autogen, elixir-format
msgid "announces"
msgstr ""
#: lib/pleroma/web/templates/embed/show.html.eex:44
#: lib/pleroma/web/templates/static_fe/static_fe/_notice.html.eex:38
#, elixir-autogen, elixir-format
msgid "likes"
msgstr ""
#: lib/pleroma/web/templates/embed/show.html.eex:42
#: lib/pleroma/web/templates/static_fe/static_fe/_notice.html.eex:36
#, elixir-autogen, elixir-format
msgid "replies"
msgstr ""
#: lib/pleroma/web/templates/embed/show.html.eex:27
#: lib/pleroma/web/templates/static_fe/static_fe/_notice.html.eex:22
#, elixir-autogen, elixir-format
msgid "sensitive media"
msgstr ""

View File

@ -3,17 +3,17 @@ msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2020-12-10 16:09+0000\n"
"PO-Revision-Date: 2020-12-11 00:56+0000\n"
"Last-Translator: ZEN <xinit.info@gmail.com>\n"
"Language-Team: Ukrainian <https://translate.pleroma.social/projects/pleroma/"
"pleroma/uk/>\n"
"PO-Revision-Date: 2022-09-18 17:09+0000\n"
"Last-Translator: Dmytro Poltavchenko <xinit.info@gmail.com>\n"
"Language-Team: Ukrainian <http://weblate.pleroma-dev.ebin.club/projects/"
"pleroma/pleroma-backend-domain-errors/uk/>\n"
"Language: uk\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=3; plural=n%10==1 && n%100!=11 ? 0 : n%10>=2 && n%10<="
"4 && (n%100<10 || n%100>=20) ? 1 : 2;\n"
"X-Generator: Weblate 4.0.4\n"
"Plural-Forms: nplurals=3; plural=n%10==1 && n%100!=11 ? 0 : n%10>=2 && n"
"%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2;\n"
"X-Generator: Weblate 4.13.1\n"
## This file is a PO Template file.
##
@ -312,7 +312,7 @@ msgstr "Цей ресурс вимагає автентифікації."
#: lib/pleroma/plugs/rate_limiter/rate_limiter.ex:206
#, elixir-format
msgid "Throttled"
msgstr "Обмежено. Перевищено ліміт запитів."
msgstr "Перевищено ліміт запитів"
#: lib/pleroma/web/common_api/common_api.ex:356
#, elixir-format

View File

@ -0,0 +1,24 @@
# Pleroma: A lightweight social networking server
# Copyright © 2017-2022 Pleroma Authors <https://pleroma.social/>
# SPDX-License-Identifier: AGPL-3.0-only
defmodule Pleroma.Repo.Migrations.DeprecateQuack do
use Ecto.Migration
alias Pleroma.ConfigDB
def up do
:quack
|> ConfigDB.get_all_by_group()
|> Enum.each(&ConfigDB.delete/1)
logger_config = ConfigDB.get_by_group_and_key(:logger, :backends)
if not is_nil(logger_config) do
%{value: backends} = logger_config
new_backends = backends -- [Quack.Logger]
{:ok, _} = ConfigDB.update_or_create(%{group: :logger, key: :backends, value: new_backends})
end
end
def down, do: :ok
end

View File

@ -8,8 +8,6 @@
config :pleroma, :second_setting, key: "value2", key2: ["Activity"]
config :quack, level: :info
config :pleroma, Pleroma.Repo, pool: Ecto.Adapters.SQL.Sandbox
config :postgrex, :json_library, Poison

View File

@ -1,2 +1,2 @@
<?xml version="1.0" encoding="UTF-8"?>
<XRD xmlns="http://docs.oasis-open.org/ns/xri/xrd-1.0"><hm:Host xmlns:hm="http://host-meta.net/xrd/1.0">framatube.org</hm:Host><Link rel="lrdd" template="http://framatube.org/main/xrd?uri={uri}"><Title>Resource Descriptor</Title></Link></XRD>
<XRD xmlns="http://docs.oasis-open.org/ns/xri/xrd-1.0"><hm:Host xmlns:hm="http://host-meta.net/xrd/1.0">framatube.org</hm:Host><Link rel="lrdd" template="https://framatube.org/main/xrd?uri={uri}"><Title>Resource Descriptor</Title></Link></XRD>

View File

@ -1,2 +1,2 @@
<?xml version="1.0" encoding="UTF-8"?>
<XRD xmlns="http://docs.oasis-open.org/ns/xri/xrd-1.0"><hm:Host xmlns:hm="http://host-meta.net/xrd/1.0">status.alpicola.com</hm:Host><Link rel="lrdd" template="http://status.alpicola.com/main/xrd?uri={uri}"><Title>Resource Descriptor</Title></Link></XRD>
<XRD xmlns="http://docs.oasis-open.org/ns/xri/xrd-1.0"><hm:Host xmlns:hm="http://host-meta.net/xrd/1.0">status.alpicola.com</hm:Host><Link rel="lrdd" template="https://status.alpicola.com/main/xrd?uri={uri}"><Title>Resource Descriptor</Title></Link></XRD>

View File

@ -0,0 +1,4 @@
<?xml version="1.0" encoding="UTF-8"?>
<XRD xmlns="http://docs.oasis-open.org/ns/xri/xrd-1.0">
<Link rel="lrdd" template="https://{{domain}}/.well-known/webfinger?resource={uri}"/>
</XRD>

92
test/fixtures/webfinger/masto-user.json vendored Normal file
View File

@ -0,0 +1,92 @@
{
"@context": [
"https://www.w3.org/ns/activitystreams",
"https://w3id.org/security/v1",
{
"manuallyApprovesFollowers": "as:manuallyApprovesFollowers",
"toot": "http://joinmastodon.org/ns#",
"featured": {
"@id": "toot:featured",
"@type": "@id"
},
"featuredTags": {
"@id": "toot:featuredTags",
"@type": "@id"
},
"alsoKnownAs": {
"@id": "as:alsoKnownAs",
"@type": "@id"
},
"movedTo": {
"@id": "as:movedTo",
"@type": "@id"
},
"schema": "http://schema.org#",
"PropertyValue": "schema:PropertyValue",
"value": "schema:value",
"IdentityProof": "toot:IdentityProof",
"discoverable": "toot:discoverable",
"Device": "toot:Device",
"Ed25519Signature": "toot:Ed25519Signature",
"Ed25519Key": "toot:Ed25519Key",
"Curve25519Key": "toot:Curve25519Key",
"EncryptedMessage": "toot:EncryptedMessage",
"publicKeyBase64": "toot:publicKeyBase64",
"deviceId": "toot:deviceId",
"claim": {
"@type": "@id",
"@id": "toot:claim"
},
"fingerprintKey": {
"@type": "@id",
"@id": "toot:fingerprintKey"
},
"identityKey": {
"@type": "@id",
"@id": "toot:identityKey"
},
"devices": {
"@type": "@id",
"@id": "toot:devices"
},
"messageFranking": "toot:messageFranking",
"messageType": "toot:messageType",
"cipherText": "toot:cipherText",
"suspended": "toot:suspended",
"focalPoint": {
"@container": "@list",
"@id": "toot:focalPoint"
}
}
],
"id": "https://{{domain}}/users/{{nickname}}",
"type": "Person",
"following": "https://{{domain}}/users/{{nickname}}/following",
"followers": "https://{{domain}}/users/{{nickname}}/followers",
"inbox": "https://{{domain}}/users/{{nickname}}/inbox",
"outbox": "https://{{domain}}/users/{{nickname}}/outbox",
"featured": "https://{{domain}}/users/{{nickname}}/collections/featured",
"featuredTags": "https://{{domain}}/users/{{nickname}}/collections/tags",
"preferredUsername": "{{nickname}}",
"name": "Name Name",
"summary": "<p>Summary</p>",
"url": "https://{{domain}}/@{{nickname}}",
"manuallyApprovesFollowers": false,
"discoverable": false,
"devices": "https://{{domain}}/users/{{nickname}}/collections/devices",
"publicKey": {
"id": "https://{{domain}}/users/{{nickname}}#main-key",
"owner": "https://{{domain}}/users/{{nickname}}",
"publicKeyPem": "-----BEGIN PUBLIC KEY-----\nMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAvwDujxmxoYHs64MyVB3L\nG5ZyBxV3ufaMRBFu42bkcTpISq1WwZ+3Zb6CI8zOO+nM+Q2llrVRYjZa4ZFnOLvM\nTq/Kf+Zf5wy2aCRer88gX+MsJOAtItSi412y0a/rKOuFaDYLOLeTkRvmGLgZWbsr\nZJOp+YWb3zQ5qsIOInkc5BwI172tMsGeFtsnbNApPV4lrmtTGaJ8RiM8MR7XANBO\nfOHggSt1+eAIKGIsCmINEMzs1mG9D75xKtC/sM8GfbvBclQcBstGkHAEj1VHPW0c\nh6Bok5/QQppicyb8UA1PAA9bznSFtKlYE4xCH8rlCDSDTBRtdnBWHKcj619Ujz4Q\nawIDAQAB\n-----END PUBLIC KEY-----\n"
},
"tag": [],
"attachment": [],
"endpoints": {
"sharedInbox": "https://{{domain}}/inbox"
},
"icon": {
"type": "Image",
"mediaType": "image/jpeg",
"url": "https://s3.wasabisys.com/merp/accounts/avatars/000/000/001/original/6fdd3eee632af247.jpg"
}
}

View File

@ -0,0 +1,23 @@
{
"subject": "acct:{{nickname}}@{{domain}}",
"aliases": [
"https://{{subdomain}}/@{{nickname}}",
"https://{{subdomain}}/users/{{nickname}}"
],
"links": [
{
"rel": "http://webfinger.net/rel/profile-page",
"type": "text/html",
"href": "https://{{subdomain}}/@{{nickname}}"
},
{
"rel": "self",
"type": "application/activity+json",
"href": "https://{{subdomain}}/users/{{nickname}}"
},
{
"rel": "http://ostatus.org/schema/1.0/subscribe",
"template": "https://{{subdomain}}/authorize_interaction?uri={uri}"
}
]
}

View File

@ -0,0 +1 @@
<?xml version="1.0" encoding="UTF-8"?><XRD xmlns="http://docs.oasis-open.org/ns/xri/xrd-1.0"><Link rel="lrdd" template="https://{{domain}}/.well-known/webfinger?resource={uri}" type="application/xrd+xml" /></XRD>

View File

@ -0,0 +1,58 @@
{
"@context": [
"https://www.w3.org/ns/activitystreams",
"https://{{domain}}/schemas/litepub-0.1.jsonld",
{
"@language": "und"
}
],
"alsoKnownAs": [],
"attachment": [],
"capabilities": {
"acceptsChatMessages": true
},
"discoverable": true,
"endpoints": {
"oauthAuthorizationEndpoint": "https://{{domain}}/oauth/authorize",
"oauthRegistrationEndpoint": "https://{{domain}}/api/v1/apps",
"oauthTokenEndpoint": "https://{{domain}}/oauth/token",
"sharedInbox": "https://{{domain}}/inbox",
"uploadMedia": "https://{{domain}}/api/ap/upload_media"
},
"followers": "https://{{domain}}/users/{{nickname}}/followers",
"following": "https://{{domain}}/users/{{nickname}}/following",
"icon": {
"type": "Image",
"url": "https://{{domain}}/media/a932a27f158b63c3a97e3a57d5384f714a82249274c6fc66c9eca581b4fd8af2.jpg"
},
"id": "https://{{domain}}/users/{{nickname}}",
"image": {
"type": "Image",
"url": "https://{{domain}}/media/db15f476d0ad14488db4762b7800479e6ef67b1824f8b9ea5c1fa05b7525c5b7.jpg"
},
"inbox": "https://{{domain}}/users/{{nickname}}/inbox",
"manuallyApprovesFollowers": false,
"name": "{{nickname}} :verified:",
"outbox": "https://{{domain}}/users/{{nickname}}/outbox",
"preferredUsername": "{{nickname}}",
"publicKey": {
"id": "https://{{domain}}/users/{{nickname}}#main-key",
"owner": "https://{{domain}}/users/{{nickname}}",
"publicKeyPem": "-----BEGIN PUBLIC KEY-----\nMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAu4XOAopC4nRIxNlHlt60\n//nCicuedu5wvLGIoQ+KUM2u7/PhLrrTDEqr1A7yQL95S0X8ryYtALgFLI5A54ww\nqjMIbIGAs44lEmDLMEd+XI+XxREE8wdsFpb4QQzWug0DTyqlMouTU25k0tfKh1rF\n4PMJ3uBSjDTAGgFvLNyFWTiVVgChbTNgGOmrEBucRl4NmKzQ69/FIUwENV88oQSU\n3bWvQTEH9rWH1rCLpkmQwdRiWfnhFX/4EUqXukfgoskvenKR8ff3nYhElDqFoE0e\nqUnIW1OZceyl8JewVLcL6m0/wdKeosTsfrcWc8DKfnRYQcBGNoBEq9GrOHDU0q2v\nyQIDAQAB\n-----END PUBLIC KEY-----\n\n"
},
"summary": "Pleroma BE dev",
"tag": [
{
"icon": {
"type": "Image",
"url": "https://{{domain}}/emoji/mine/6143373a807b1ae7.png"
},
"id": "https://{{domain}}/emoji/mine/6143373a807b1ae7.png",
"name": ":verified:",
"type": "Emoji",
"updated": "1970-01-01T00:00:00Z"
}
],
"type": "Person",
"url": "https://{{domain}}/users/{{nickname}}"
}

View File

@ -0,0 +1,27 @@
{
"aliases": [
"https://{{subdomain}}/users/{{nickname}}"
],
"links": [
{
"href": "https://{{subdomain}}/users/{{nickname}}",
"rel": "http://webfinger.net/rel/profile-page",
"type": "text/html"
},
{
"href": "https://{{subdomain}}/users/{{nickname}}",
"rel": "self",
"type": "application/activity+json"
},
{
"href": "https://{{subdomain}}/users/{{nickname}}",
"rel": "self",
"type": "application/ld+json; profile=\"https://www.w3.org/ns/activitystreams\""
},
{
"rel": "http://ostatus.org/schema/1.0/subscribe",
"template": "https://{{subdomain}}/ostatus_subscribe?acct={uri}"
}
],
"subject": "acct:{{nickname}}@{{domain}}"
}

View File

@ -49,7 +49,6 @@ test "error if file with custom settings doesn't exist" do
describe "migrate_to_db/1" do
setup do
clear_config(:configurable_from_database, true)
clear_config([:quack, :level])
end
@tag capture_log: true
@ -72,14 +71,12 @@ test "filtered settings are migrated to db" do
config1 = ConfigDB.get_by_params(%{group: ":pleroma", key: ":first_setting"})
config2 = ConfigDB.get_by_params(%{group: ":pleroma", key: ":second_setting"})
config3 = ConfigDB.get_by_params(%{group: ":quack", key: ":level"})
refute ConfigDB.get_by_params(%{group: ":pleroma", key: "Pleroma.Repo"})
refute ConfigDB.get_by_params(%{group: ":postgrex", key: ":json_library"})
refute ConfigDB.get_by_params(%{group: ":pleroma", key: ":database"})
assert config1.value == [key: "value", key2: [Repo]]
assert config2.value == [key: "value2", key2: ["Activity"]]
assert config3.value == :info
end
test "config table is truncated before migration" do
@ -108,7 +105,6 @@ test "config table is truncated before migration" do
test "settings are migrated to file and deleted from db", %{temp_file: temp_file} do
insert_config_record(:pleroma, :setting_first, key: "value", key2: ["Activity"])
insert_config_record(:pleroma, :setting_second, key: "value2", key2: [Repo])
insert_config_record(:quack, :level, :info)
MixTask.run(["migrate_from_db", "--env", "temp", "-d"])
@ -117,7 +113,6 @@ test "settings are migrated to file and deleted from db", %{temp_file: temp_file
file = File.read!(temp_file)
assert file =~ "config :pleroma, :setting_first,"
assert file =~ "config :pleroma, :setting_second,"
assert file =~ "config :quack, :level, :info"
end
test "load a settings with large values and pass to file", %{temp_file: temp_file} do
@ -199,7 +194,6 @@ test "load a settings with large values and pass to file", %{temp_file: temp_fil
setup do
insert_config_record(:pleroma, :setting_first, key: "value", key2: ["Activity"])
insert_config_record(:pleroma, :setting_second, key: "value2", key2: [Repo])
insert_config_record(:quack, :level, :info)
path = "test/instance_static"
file_path = Path.join(path, "temp.exported_from_db.secret.exs")
@ -215,7 +209,6 @@ test "with path parameter", %{file_path: file_path} do
file = File.read!(file_path)
assert file =~ "config :pleroma, :setting_first,"
assert file =~ "config :pleroma, :setting_second,"
assert file =~ "config :quack, :level, :info"
end
test "release", %{file_path: file_path} do
@ -227,7 +220,6 @@ test "release", %{file_path: file_path} do
file = File.read!(file_path)
assert file =~ "config :pleroma, :setting_first,"
assert file =~ "config :pleroma, :setting_second,"
assert file =~ "config :quack, :level, :info"
end
end

View File

@ -11,7 +11,6 @@ test "read/1" do
config = Loader.read("test/fixtures/config/temp.secret.exs")
assert config[:pleroma][:first_setting][:key] == "value"
assert config[:pleroma][:first_setting][:key2] == [Pleroma.Repo]
assert config[:quack][:level] == :info
end
test "filter_group/2" do

View File

@ -15,13 +15,11 @@ defmodule Pleroma.Config.TransferTaskTest do
test "transfer config values from db to env" do
refute Application.get_env(:pleroma, :test_key)
refute Application.get_env(:idna, :test_key)
refute Application.get_env(:quack, :test_key)
refute Application.get_env(:postgrex, :test_key)
initial = Application.get_env(:logger, :level)
insert(:config, key: :test_key, value: [live: 2, com: 3])
insert(:config, group: :idna, key: :test_key, value: [live: 15, com: 35])
insert(:config, group: :quack, key: :test_key, value: [:test_value1, :test_value2])
insert(:config, group: :postgrex, key: :test_key, value: :value)
insert(:config, group: :logger, key: :level, value: :debug)
@ -29,36 +27,32 @@ test "transfer config values from db to env" do
assert Application.get_env(:pleroma, :test_key) == [live: 2, com: 3]
assert Application.get_env(:idna, :test_key) == [live: 15, com: 35]
assert Application.get_env(:quack, :test_key) == [:test_value1, :test_value2]
assert Application.get_env(:logger, :level) == :debug
assert Application.get_env(:postgrex, :test_key) == :value
on_exit(fn ->
Application.delete_env(:pleroma, :test_key)
Application.delete_env(:idna, :test_key)
Application.delete_env(:quack, :test_key)
Application.delete_env(:postgrex, :test_key)
Application.put_env(:logger, :level, initial)
end)
end
test "transfer config values for 1 group and some keys" do
level = Application.get_env(:quack, :level)
meta = Application.get_env(:quack, :meta)
level = Application.get_env(:somegroup, :level)
meta = Application.get_env(:somegroup, :meta)
insert(:config, group: :quack, key: :level, value: :info)
insert(:config, group: :quack, key: :meta, value: [:none])
insert(:config, group: :somegroup, key: :level, value: :info)
insert(:config, group: :somegroup, key: :meta, value: [:none])
TransferTask.start_link([])
assert Application.get_env(:quack, :level) == :info
assert Application.get_env(:quack, :meta) == [:none]
default = Pleroma.Config.Holder.default_config(:quack, :webhook_url)
assert Application.get_env(:quack, :webhook_url) == default
assert Application.get_env(:somegroup, :level) == :info
assert Application.get_env(:somegroup, :meta) == [:none]
on_exit(fn ->
Application.put_env(:quack, :level, level)
Application.put_env(:quack, :meta, meta)
Application.put_env(:somegroup, :level, level)
Application.put_env(:somegroup, :meta, meta)
end)
end

View File

@ -16,13 +16,13 @@ test "get_by_params/1" do
test "get_all_as_keyword/0" do
saved = insert(:config)
insert(:config, group: ":quack", key: ":level", value: :info)
insert(:config, group: ":quack", key: ":meta", value: [:none])
insert(:config, group: ":goose", key: ":level", value: :info)
insert(:config, group: ":goose", key: ":meta", value: [:none])
insert(:config,
group: ":quack",
group: ":goose",
key: ":webhook_url",
value: "https://hooks.slack.com/services/KEY/some_val"
value: "https://gander.com/"
)
config = ConfigDB.get_all_as_keyword()
@ -31,9 +31,9 @@ test "get_all_as_keyword/0" do
{saved.key, saved.value}
]
assert config[:quack][:level] == :info
assert config[:quack][:meta] == [:none]
assert config[:quack][:webhook_url] == "https://hooks.slack.com/services/KEY/some_val"
assert config[:goose][:level] == :info
assert config[:goose][:meta] == [:none]
assert config[:goose][:webhook_url] == "https://gander.com/"
end
describe "update_or_create/1" do
@ -267,10 +267,6 @@ test "ExSyslogger module" do
assert ConfigDB.to_elixir_types("ExSyslogger") == ExSyslogger
end
test "Quack.Logger module" do
assert ConfigDB.to_elixir_types("Quack.Logger") == Quack.Logger
end
test "Swoosh.Adapters modules" do
assert ConfigDB.to_elixir_types("Swoosh.Adapters.SMTP") == Swoosh.Adapters.SMTP
assert ConfigDB.to_elixir_types("Swoosh.Adapters.AmazonSES") == Swoosh.Adapters.AmazonSES

View File

@ -6,6 +6,7 @@ defmodule Pleroma.Object.FetcherTest do
use Pleroma.DataCase
alias Pleroma.Activity
alias Pleroma.Instances
alias Pleroma.Object
alias Pleroma.Object.Fetcher
@ -159,6 +160,17 @@ test "it does not fetch a spoofed object uploaded on an instance as an attachmen
"https://patch.cx/media/03ca3c8b4ac3ddd08bf0f84be7885f2f88de0f709112131a22d83650819e36c2.json"
)
end
test "it resets instance reachability on successful fetch" do
id = "http://mastodon.example.org/@admin/99541947525187367"
Instances.set_consistently_unreachable(id)
refute Instances.reachable?(id)
{:ok, object} =
Fetcher.fetch_object_from_id("http://mastodon.example.org/@admin/99541947525187367")
assert Instances.reachable?(id)
end
end
describe "implementation quirks" do

View File

@ -859,6 +859,116 @@ test "gets an existing user by nickname starting with http" do
end
end
describe "get_or_fetch/1 remote users with tld, while BE is runned on subdomain" do
setup do: clear_config([Pleroma.Web.WebFinger, :update_nickname_on_user_fetch], true)
test "for mastodon" do
Tesla.Mock.mock(fn
%{url: "https://example.com/.well-known/host-meta"} ->
%Tesla.Env{
status: 302,
headers: [{"location", "https://sub.example.com/.well-known/host-meta"}]
}
%{url: "https://sub.example.com/.well-known/host-meta"} ->
%Tesla.Env{
status: 200,
body:
"test/fixtures/webfinger/masto-host-meta.xml"
|> File.read!()
|> String.replace("{{domain}}", "sub.example.com")
}
%{url: "https://sub.example.com/.well-known/webfinger?resource=acct:a@example.com"} ->
%Tesla.Env{
status: 200,
body:
"test/fixtures/webfinger/masto-webfinger.json"
|> File.read!()
|> String.replace("{{nickname}}", "a")
|> String.replace("{{domain}}", "example.com")
|> String.replace("{{subdomain}}", "sub.example.com"),
headers: [{"content-type", "application/jrd+json"}]
}
%{url: "https://sub.example.com/users/a"} ->
%Tesla.Env{
status: 200,
body:
"test/fixtures/webfinger/masto-user.json"
|> File.read!()
|> String.replace("{{nickname}}", "a")
|> String.replace("{{domain}}", "sub.example.com"),
headers: [{"content-type", "application/activity+json"}]
}
%{url: "https://sub.example.com/users/a/collections/featured"} ->
%Tesla.Env{
status: 200,
body:
File.read!("test/fixtures/users_mock/masto_featured.json")
|> String.replace("{{domain}}", "sub.example.com")
|> String.replace("{{nickname}}", "a"),
headers: [{"content-type", "application/activity+json"}]
}
end)
ap_id = "a@example.com"
{:ok, fetched_user} = User.get_or_fetch(ap_id)
assert fetched_user.ap_id == "https://sub.example.com/users/a"
assert fetched_user.nickname == "a@example.com"
end
test "for pleroma" do
Tesla.Mock.mock(fn
%{url: "https://example.com/.well-known/host-meta"} ->
%Tesla.Env{
status: 302,
headers: [{"location", "https://sub.example.com/.well-known/host-meta"}]
}
%{url: "https://sub.example.com/.well-known/host-meta"} ->
%Tesla.Env{
status: 200,
body:
"test/fixtures/webfinger/pleroma-host-meta.xml"
|> File.read!()
|> String.replace("{{domain}}", "sub.example.com")
}
%{url: "https://sub.example.com/.well-known/webfinger?resource=acct:a@example.com"} ->
%Tesla.Env{
status: 200,
body:
"test/fixtures/webfinger/pleroma-webfinger.json"
|> File.read!()
|> String.replace("{{nickname}}", "a")
|> String.replace("{{domain}}", "example.com")
|> String.replace("{{subdomain}}", "sub.example.com"),
headers: [{"content-type", "application/jrd+json"}]
}
%{url: "https://sub.example.com/users/a"} ->
%Tesla.Env{
status: 200,
body:
"test/fixtures/webfinger/pleroma-user.json"
|> File.read!()
|> String.replace("{{nickname}}", "a")
|> String.replace("{{domain}}", "sub.example.com"),
headers: [{"content-type", "application/activity+json"}]
}
end)
ap_id = "a@example.com"
{:ok, fetched_user} = User.get_or_fetch(ap_id)
assert fetched_user.ap_id == "https://sub.example.com/users/a"
assert fetched_user.nickname == "a@example.com"
end
end
describe "fetching a user from nickname or trying to build one" do
test "gets an existing user" do
user = insert(:user)

View File

@ -317,14 +317,14 @@ test "create new config setting in db", %{conn: conn} do
end
test "save configs setting without explicit key", %{conn: conn} do
level = Application.get_env(:quack, :level)
meta = Application.get_env(:quack, :meta)
webhook_url = Application.get_env(:quack, :webhook_url)
adapter = Application.get_env(:http, :adapter)
send_user_agent = Application.get_env(:http, :send_user_agent)
user_agent = Application.get_env(:http, :user_agent)
on_exit(fn ->
Application.put_env(:quack, :level, level)
Application.put_env(:quack, :meta, meta)
Application.put_env(:quack, :webhook_url, webhook_url)
Application.put_env(:http, :adapter, adapter)
Application.put_env(:http, :send_user_agent, send_user_agent)
Application.put_env(:http, :user_agent, user_agent)
end)
conn =
@ -333,19 +333,19 @@ test "save configs setting without explicit key", %{conn: conn} do
|> post("/api/pleroma/admin/config", %{
configs: [
%{
group: ":quack",
key: ":level",
value: ":info"
group: ":http",
key: ":adapter",
value: [":someval"]
},
%{
group: ":quack",
key: ":meta",
value: [":none"]
group: ":http",
key: ":send_user_agent",
value: true
},
%{
group: ":quack",
key: ":webhook_url",
value: "https://hooks.slack.com/services/KEY"
group: ":http",
key: ":user_agent",
value: [":default"]
}
]
})
@ -353,30 +353,30 @@ test "save configs setting without explicit key", %{conn: conn} do
assert json_response_and_validate_schema(conn, 200) == %{
"configs" => [
%{
"group" => ":quack",
"key" => ":level",
"value" => ":info",
"db" => [":level"]
"group" => ":http",
"key" => ":adapter",
"value" => [":someval"],
"db" => [":adapter"]
},
%{
"group" => ":quack",
"key" => ":meta",
"value" => [":none"],
"db" => [":meta"]
"group" => ":http",
"key" => ":send_user_agent",
"value" => true,
"db" => [":send_user_agent"]
},
%{
"group" => ":quack",
"key" => ":webhook_url",
"value" => "https://hooks.slack.com/services/KEY",
"db" => [":webhook_url"]
"group" => ":http",
"key" => ":user_agent",
"value" => [":default"],
"db" => [":user_agent"]
}
],
"need_reboot" => false
}
assert Application.get_env(:quack, :level) == :info
assert Application.get_env(:quack, :meta) == [:none]
assert Application.get_env(:quack, :webhook_url) == "https://hooks.slack.com/services/KEY"
assert Application.get_env(:http, :adapter) == [:someval]
assert Application.get_env(:http, :send_user_agent) == true
assert Application.get_env(:http, :user_agent) == [:default]
end
test "saving config with partial update", %{conn: conn} do

View File

@ -54,6 +54,32 @@ test "returns report by its id", %{conn: conn} do
assert notes["content"] == "this is an admin note"
end
test "renders reported content even if the status is deleted", %{conn: conn} do
[reporter, target_user] = insert_pair(:user)
activity = insert(:note_activity, user: target_user)
activity = Activity.normalize(activity)
{:ok, %{id: report_id}} =
CommonAPI.report(reporter, %{
account_id: target_user.id,
comment: "I feel offended",
status_ids: [activity.id]
})
CommonAPI.delete(activity.id, target_user)
response =
conn
|> get("/api/pleroma/admin/reports/#{report_id}")
|> json_response_and_validate_schema(:ok)
assert response["id"] == report_id
assert [status] = response["statuses"]
assert activity.data["id"] == status["uri"]
assert activity.object.data["content"] == status["content"]
end
test "returns 404 when report id is invalid", %{conn: conn} do
conn = get(conn, "/api/pleroma/admin/reports/test")

View File

@ -1154,6 +1154,32 @@ test "updates report state" do
assert activity_id == activity.data["id"]
end
test "updates report state, don't strip when report_strip_status is false" do
clear_config([:instance, :report_strip_status], false)
[reporter, target_user] = insert_pair(:user)
activity = insert(:note_activity, user: target_user)
{:ok, %Activity{id: report_id, data: report_data}} =
CommonAPI.report(reporter, %{
account_id: target_user.id,
comment: "I feel offended",
status_ids: [activity.id]
})
{:ok, report} = CommonAPI.update_report_state(report_id, "resolved")
assert report.data["state"] == "resolved"
[reported_user, reported_activity] = report.data["object"]
assert reported_user == target_user.ap_id
assert is_map(reported_activity)
assert reported_activity["content"] ==
report_data["object"] |> Enum.at(1) |> Map.get("content")
end
test "does not update report state when state is unsupported" do
[reporter, target_user] = insert_pair(:user)
activity = insert(:note_activity, user: target_user)

View File

@ -59,9 +59,9 @@ test "it sends `report-to` & `report-uri` CSP response headers", %{conn: conn} d
assert csp =~ ~r|report-uri https://endpoint.com;report-to csp-endpoint;|
[reply_to] = Conn.get_resp_header(conn, "reply-to")
[report_to] = Conn.get_resp_header(conn, "report-to")
assert reply_to ==
assert report_to ==
"{\"endpoints\":[{\"url\":\"https://endpoint.com\"}],\"group\":\"csp-endpoint\",\"max-age\":10886400}"
end

View File

@ -3,7 +3,7 @@
# SPDX-License-Identifier: AGPL-3.0-only
defmodule Pleroma.Web.TwitterAPI.RemoteFollowControllerTest do
use Pleroma.Web.ConnCase
use Pleroma.Web.ConnCase, async: true
alias Pleroma.MFA
alias Pleroma.MFA.TOTP

View File

@ -48,6 +48,35 @@ test "Webfinger JRD" do
]
end
test "reach user on tld, while pleroma is runned on subdomain" do
Pleroma.Web.Endpoint.config_change(
[{Pleroma.Web.Endpoint, url: [host: "sub.example.com"]}],
[]
)
clear_config([Pleroma.Web.Endpoint, :url, :host], "sub.example.com")
clear_config([Pleroma.Web.WebFinger, :domain], "example.com")
user = insert(:user, ap_id: "https://sub.example.com/users/bobby", nickname: "bobby")
response =
build_conn()
|> put_req_header("accept", "application/jrd+json")
|> get("/.well-known/webfinger?resource=acct:#{user.nickname}@example.com")
|> json_response(200)
assert response["subject"] == "acct:#{user.nickname}@example.com"
assert response["aliases"] == ["https://sub.example.com/users/#{user.nickname}"]
on_exit(fn ->
Pleroma.Web.Endpoint.config_change(
[{Pleroma.Web.Endpoint, url: [host: "localhost"]}],
[]
)
end)
end
test "it returns 404 when user isn't found (JSON)" do
result =
build_conn()

View File

@ -47,7 +47,7 @@ test "returns error for nonsensical input" do
test "returns error when there is no content-type header" do
Tesla.Mock.mock(fn
%{url: "http://social.heldscal.la/.well-known/host-meta"} ->
%{url: "https://social.heldscal.la/.well-known/host-meta"} ->
{:ok,
%Tesla.Env{
status: 200,
@ -120,7 +120,7 @@ test "it gets the xrd endpoint for hubzilla" do
test "it gets the xrd endpoint for statusnet" do
{:ok, template} = WebFinger.find_lrdd_template("status.alpicola.com")
assert template == "http://status.alpicola.com/main/xrd?uri={uri}"
assert template == "https://status.alpicola.com/main/xrd?uri={uri}"
end
test "it works with idna domains as nickname" do
@ -147,7 +147,7 @@ test "respects json content-type" do
headers: [{"content-type", "application/jrd+json"}]
}}
%{url: "http://mastodon.social/.well-known/host-meta"} ->
%{url: "https://mastodon.social/.well-known/host-meta"} ->
{:ok,
%Tesla.Env{
status: 200,
@ -170,7 +170,7 @@ test "respects xml content-type" do
headers: [{"content-type", "application/xrd+xml"}]
}}
%{url: "http://pawoo.net/.well-known/host-meta"} ->
%{url: "https://pawoo.net/.well-known/host-meta"} ->
{:ok,
%Tesla.Env{
status: 200,

View File

@ -0,0 +1,40 @@
# Pleroma: A lightweight social networking server
# Copyright © 2017-2022 Pleroma Authors <https://pleroma.social/>
# SPDX-License-Identifier: AGPL-3.0-only
defmodule Pleroma.Workers.PublisherWorkerTest do
use Pleroma.DataCase, async: true
use Oban.Testing, repo: Pleroma.Repo
import Pleroma.Factory
alias Pleroma.Object
alias Pleroma.Web.ActivityPub.ActivityPub
alias Pleroma.Web.ActivityPub.Builder
alias Pleroma.Web.CommonAPI
alias Pleroma.Web.Federator
describe "Oban job priority:" do
setup do
user = insert(:user)
{:ok, post} = CommonAPI.post(user, %{status: "Regrettable post"})
object = Object.normalize(post, fetch: false)
{:ok, delete_data, _meta} = Builder.delete(user, object.data["id"])
{:ok, delete, _meta} = ActivityPub.persist(delete_data, local: true)
%{
post: post,
delete: delete
}
end
test "Deletions are lower priority", %{delete: delete} do
assert {:ok, %Oban.Job{priority: 3}} = Federator.publish(delete)
end
test "Creates are normal priority", %{post: post} do
assert {:ok, %Oban.Job{priority: 0}} = Federator.publish(post)
end
end
end

View File

@ -424,14 +424,6 @@ def get("http://mastodon.example.org/users/gargron", _, _, [
{:error, :nxdomain}
end
def get("http://osada.macgirvin.com/.well-known/host-meta", _, _, _) do
{:ok,
%Tesla.Env{
status: 404,
body: ""
}}
end
def get("https://osada.macgirvin.com/.well-known/host-meta", _, _, _) do
{:ok,
%Tesla.Env{
@ -765,7 +757,7 @@ def get(
{:ok, %Tesla.Env{status: 406, body: ""}}
end
def get("http://squeet.me/.well-known/host-meta", _, _, _) do
def get("https://squeet.me/.well-known/host-meta", _, _, _) do
{:ok,
%Tesla.Env{status: 200, body: File.read!("test/fixtures/tesla_mock/squeet.me_host_meta")}}
end
@ -806,7 +798,7 @@ def get(
{:ok, %Tesla.Env{status: 200, body: "", headers: [{"content-type", "application/jrd+json"}]}}
end
def get("http://framatube.org/.well-known/host-meta", _, _, _) do
def get("https://framatube.org/.well-known/host-meta", _, _, _) do
{:ok,
%Tesla.Env{
status: 200,
@ -815,7 +807,7 @@ def get("http://framatube.org/.well-known/host-meta", _, _, _) do
end
def get(
"http://framatube.org/main/xrd?uri=acct:framasoft@framatube.org",
"https://framatube.org/main/xrd?uri=acct:framasoft@framatube.org",
_,
_,
[{"accept", "application/xrd+xml,application/jrd+json"}]
@ -850,7 +842,7 @@ def get(
}}
end
def get("http://status.alpicola.com/.well-known/host-meta", _, _, _) do
def get("https://status.alpicola.com/.well-known/host-meta", _, _, _) do
{:ok,
%Tesla.Env{
status: 200,
@ -858,7 +850,7 @@ def get("http://status.alpicola.com/.well-known/host-meta", _, _, _) do
}}
end
def get("http://macgirvin.com/.well-known/host-meta", _, _, _) do
def get("https://macgirvin.com/.well-known/host-meta", _, _, _) do
{:ok,
%Tesla.Env{
status: 200,
@ -866,7 +858,7 @@ def get("http://macgirvin.com/.well-known/host-meta", _, _, _) do
}}
end
def get("http://gerzilla.de/.well-known/host-meta", _, _, _) do
def get("https://gerzilla.de/.well-known/host-meta", _, _, _) do
{:ok,
%Tesla.Env{
status: 200,