Merge branch 'develop' of https://git.pleroma.social/pleroma/pleroma into develop
This commit is contained in:
commit
d0ffefc270
120 changed files with 820 additions and 309 deletions
31
CHANGELOG.md
31
CHANGELOG.md
|
@ -3,16 +3,41 @@ All notable changes to this project will be documented in this file.
|
|||
|
||||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
|
||||
|
||||
## unreleased-patch - ???
|
||||
## Unreleased
|
||||
|
||||
### Changed
|
||||
|
||||
- Renamed `:await_up_timeout` in `:connections_pool` namespace to `:connect_timeout`, old name is deprecated.
|
||||
- Renamed `:timeout` in `pools` namespace to `:recv_timeout`, old name is deprecated.
|
||||
|
||||
### Removed
|
||||
|
||||
- **Breaking:** Removed `Pleroma.Workers.Cron.StatsWorker` setting from Oban `:crontab`.
|
||||
|
||||
## [2.1.1] - 2020-09-08
|
||||
|
||||
### Security
|
||||
- Fix possible DoS in Mastodon API user search due to an error in match clauses, leading to an infinite recursion and subsequent OOM with certain inputs.
|
||||
- Fix metadata leak for accounts and statuses on private instances.
|
||||
- Fix possible DoS in Admin API search using an atom leak vulnerability. Authentication with admin rights was required to exploit.
|
||||
|
||||
### Changed
|
||||
|
||||
- **Breaking:** The metadata providers RelMe and Feed are no longer configurable. RelMe should always be activated and Feed only provides a <link> header tag for the actual RSS/Atom feed when the instance is public.
|
||||
- Improved error message when cmake is not available at build stage.
|
||||
|
||||
### Added
|
||||
- Rich media failure tracking (along with `:failure_backoff` option)
|
||||
- Rich media failure tracking (along with `:failure_backoff` option).
|
||||
|
||||
### Fixed
|
||||
- Default HTTP adapter not respecting pool setting, leading to possible OOM.
|
||||
- Fixed uploading webp images when the Exiftool Upload Filter is enabled by skipping them
|
||||
- Mastodon API: Search parameter `following` now correctly returns the followings rather than the followers
|
||||
- Mastodon API: Timelines hanging for (`number of posts with links * rich media timeout`) in the worst case.
|
||||
Reduced to just rich media timeout.
|
||||
- Password resets no longer processed for deactivated accounts
|
||||
- Mastodon API: Cards being wrong for preview statuses due to cache key collision.
|
||||
- Password resets no longer processed for deactivated accounts.
|
||||
- Favicon scraper raising exceptions on URLs longer than 255 characters.
|
||||
|
||||
## [2.1.0] - 2020-08-28
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@ Currently, Pleroma offers bugfixes and security patches only for the latest mino
|
|||
|
||||
| Version | Support
|
||||
|---------| --------
|
||||
| 2.0 | Bugfixes and security patches
|
||||
| 2.1 | Bugfixes and security patches
|
||||
|
||||
## Reporting a vulnerability
|
||||
|
||||
|
|
|
@ -457,9 +457,7 @@
|
|||
config :pleroma, Pleroma.Web.Metadata,
|
||||
providers: [
|
||||
Pleroma.Web.Metadata.Providers.OpenGraph,
|
||||
Pleroma.Web.Metadata.Providers.TwitterCard,
|
||||
Pleroma.Web.Metadata.Providers.RelMe,
|
||||
Pleroma.Web.Metadata.Providers.Feed
|
||||
Pleroma.Web.Metadata.Providers.TwitterCard
|
||||
],
|
||||
unfurl_nsfw: false
|
||||
|
||||
|
@ -549,7 +547,6 @@
|
|||
plugins: [Oban.Plugins.Pruner],
|
||||
crontab: [
|
||||
{"0 0 * * *", Pleroma.Workers.Cron.ClearOauthTokenWorker},
|
||||
{"0 * * * *", Pleroma.Workers.Cron.StatsWorker},
|
||||
{"* * * * *", Pleroma.Workers.Cron.PurgeExpiredActivitiesWorker},
|
||||
{"0 0 * * 0", Pleroma.Workers.Cron.DigestEmailsWorker},
|
||||
{"0 0 * * *", Pleroma.Workers.Cron.NewUsersDigestWorker}
|
||||
|
@ -739,28 +736,28 @@
|
|||
max_connections: 250,
|
||||
max_idle_time: 30_000,
|
||||
retry: 0,
|
||||
await_up_timeout: 5_000
|
||||
connect_timeout: 5_000
|
||||
|
||||
config :pleroma, :pools,
|
||||
federation: [
|
||||
size: 50,
|
||||
max_waiting: 10,
|
||||
timeout: 10_000
|
||||
recv_timeout: 10_000
|
||||
],
|
||||
media: [
|
||||
size: 50,
|
||||
max_waiting: 10,
|
||||
timeout: 10_000
|
||||
recv_timeout: 10_000
|
||||
],
|
||||
upload: [
|
||||
size: 25,
|
||||
max_waiting: 5,
|
||||
timeout: 15_000
|
||||
recv_timeout: 15_000
|
||||
],
|
||||
default: [
|
||||
size: 10,
|
||||
max_waiting: 2,
|
||||
timeout: 5_000
|
||||
recv_timeout: 5_000
|
||||
]
|
||||
|
||||
config :pleroma, :hackney_pools,
|
||||
|
|
|
@ -2291,7 +2291,6 @@
|
|||
description: "Settings for cron background jobs",
|
||||
suggestions: [
|
||||
{"0 0 * * *", Pleroma.Workers.Cron.ClearOauthTokenWorker},
|
||||
{"0 * * * *", Pleroma.Workers.Cron.StatsWorker},
|
||||
{"* * * * *", Pleroma.Workers.Cron.PurgeExpiredActivitiesWorker},
|
||||
{"0 0 * * 0", Pleroma.Workers.Cron.DigestEmailsWorker},
|
||||
{"0 0 * * *", Pleroma.Workers.Cron.NewUsersDigestWorker}
|
||||
|
@ -3378,7 +3377,7 @@
|
|||
suggestions: [250]
|
||||
},
|
||||
%{
|
||||
key: :await_up_timeout,
|
||||
key: :connect_timeout,
|
||||
type: :integer,
|
||||
description: "Timeout while `gun` will wait until connection is up. Default: 5000ms.",
|
||||
suggestions: [5000]
|
||||
|
@ -3416,6 +3415,12 @@
|
|||
description:
|
||||
"Maximum number of requests waiting for other requests to finish. After this number is reached, the pool will start returning errrors when a new request is made",
|
||||
suggestions: [10]
|
||||
},
|
||||
%{
|
||||
key: :recv_timeout,
|
||||
type: :integer,
|
||||
description: "Timeout for the pool while gun will wait for response",
|
||||
suggestions: [10_000]
|
||||
}
|
||||
]
|
||||
}
|
||||
|
|
|
@ -114,8 +114,6 @@
|
|||
|
||||
config :pleroma, Pleroma.Web.ApiSpec.CastAndValidate, strict: true
|
||||
|
||||
config :pleroma, :instances_favicons, enabled: true
|
||||
|
||||
config :pleroma, Pleroma.Uploaders.S3,
|
||||
bucket: nil,
|
||||
streaming_enabled: true,
|
||||
|
|
|
@ -115,6 +115,7 @@ To add configuration to your config file, you can copy it from the base config.
|
|||
* `Pleroma.Web.ActivityPub.MRF.VocabularyPolicy`: Restricts activities to a configured set of vocabulary. (See [`:mrf_vocabulary`](#mrf_vocabulary)).
|
||||
* `Pleroma.Web.ActivityPub.MRF.ObjectAgePolicy`: Rejects or delists posts based on their age when received. (See [`:mrf_object_age`](#mrf_object_age)).
|
||||
* `Pleroma.Web.ActivityPub.MRF.ActivityExpirationPolicy`: Sets a default expiration on all posts made by users of the local instance. Requires `Pleroma.ActivityExpiration` to be enabled for processing the scheduled delections.
|
||||
* `Pleroma.Web.ActivityPub.MRF.ForceBotUnlistedPolicy`: Makes all bot posts to disappear from public timelines.
|
||||
* `transparency`: Make the content of your Message Rewrite Facility settings public (via nodeinfo).
|
||||
* `transparency_exclusions`: Exclude specific instance names from MRF transparency. The use of the exclusions feature will be disclosed in nodeinfo as a boolean value.
|
||||
|
||||
|
@ -352,8 +353,6 @@ config :pleroma, Pleroma.Web.MediaProxy.Invalidation.Http,
|
|||
* `providers`: a list of metadata providers to enable. Providers available:
|
||||
* `Pleroma.Web.Metadata.Providers.OpenGraph`
|
||||
* `Pleroma.Web.Metadata.Providers.TwitterCard`
|
||||
* `Pleroma.Web.Metadata.Providers.RelMe` - add links from user bio with rel=me into the `<header>` as `<link rel=me>`.
|
||||
* `Pleroma.Web.Metadata.Providers.Feed` - add a link to a user's Atom feed into the `<header>` as `<link rel=alternate>`.
|
||||
* `unfurl_nsfw`: If set to `true` nsfw attachments will be shown in previews.
|
||||
|
||||
### :rich_media (consumer)
|
||||
|
@ -498,7 +497,7 @@ Settings for HTTP connection pool.
|
|||
* `:connection_acquisition_wait` - Timeout to acquire a connection from pool.The total max time is this value multiplied by the number of retries.
|
||||
* `connection_acquisition_retries` - Number of attempts to acquire the connection from the pool if it is overloaded. Each attempt is timed `:connection_acquisition_wait` apart.
|
||||
* `:max_connections` - Maximum number of connections in the pool.
|
||||
* `:await_up_timeout` - Timeout to connect to the host.
|
||||
* `:connect_timeout` - Timeout to connect to the host.
|
||||
* `:reclaim_multiplier` - Multiplied by `:max_connections` this will be the maximum number of idle connections that will be reclaimed in case the pool is overloaded.
|
||||
|
||||
### :pools
|
||||
|
@ -517,7 +516,7 @@ There are four pools used:
|
|||
For each pool, the options are:
|
||||
|
||||
* `:size` - limit to how much requests can be concurrently executed.
|
||||
* `:timeout` - timeout while `gun` will wait for response
|
||||
* `:recv_timeout` - timeout while `gun` will wait for response
|
||||
* `:max_waiting` - limit to how much requests can be waiting for others to finish, after this is reached, subsequent requests will be dropped.
|
||||
|
||||
## Captcha
|
||||
|
|
|
@ -18,6 +18,7 @@ defmodule Mix.Pleroma do
|
|||
@doc "Common functions to be reused in mix tasks"
|
||||
def start_pleroma do
|
||||
Pleroma.Config.Holder.save_default()
|
||||
Pleroma.Config.Oban.warn()
|
||||
Application.put_env(:phoenix, :serve_endpoints, false, persistent: true)
|
||||
|
||||
if Pleroma.Config.get(:env) != :test do
|
||||
|
|
|
@ -91,20 +91,17 @@ def run(["adapters"]) do
|
|||
"Without conn and without pool" => fn ->
|
||||
{:ok, %Tesla.Env{}} =
|
||||
Pleroma.HTTP.get("https://httpbin.org/stream-bytes/1500", [],
|
||||
adapter: [pool: :no_pool, receive_conn: false]
|
||||
pool: :no_pool,
|
||||
receive_conn: false
|
||||
)
|
||||
end,
|
||||
"Without conn and with pool" => fn ->
|
||||
{:ok, %Tesla.Env{}} =
|
||||
Pleroma.HTTP.get("https://httpbin.org/stream-bytes/1500", [],
|
||||
adapter: [receive_conn: false]
|
||||
)
|
||||
Pleroma.HTTP.get("https://httpbin.org/stream-bytes/1500", [], receive_conn: false)
|
||||
end,
|
||||
"With reused conn and without pool" => fn ->
|
||||
{:ok, %Tesla.Env{}} =
|
||||
Pleroma.HTTP.get("https://httpbin.org/stream-bytes/1500", [],
|
||||
adapter: [pool: :no_pool]
|
||||
)
|
||||
Pleroma.HTTP.get("https://httpbin.org/stream-bytes/1500", [], pool: :no_pool)
|
||||
end,
|
||||
"With reused conn and with pool" => fn ->
|
||||
{:ok, %Tesla.Env{}} = Pleroma.HTTP.get("https://httpbin.org/stream-bytes/1500")
|
||||
|
|
|
@ -124,9 +124,7 @@ defp download_build(frontend_info, dest) do
|
|||
url = String.replace(frontend_info["build_url"], "${ref}", frontend_info["ref"])
|
||||
|
||||
with {:ok, %{status: 200, body: zip_body}} <-
|
||||
Pleroma.HTTP.get(url, [],
|
||||
adapter: [pool: :media, timeout: 120_000, recv_timeout: 120_000]
|
||||
) do
|
||||
Pleroma.HTTP.get(url, [], pool: :media, recv_timeout: 120_000) do
|
||||
unzip(zip_body, dest)
|
||||
else
|
||||
e -> {:error, e}
|
||||
|
|
|
@ -50,6 +50,7 @@ def start(_type, _args) do
|
|||
Pleroma.Telemetry.Logger.attach()
|
||||
Config.Holder.save_default()
|
||||
Pleroma.HTML.compile_scrubbers()
|
||||
Pleroma.Config.Oban.warn()
|
||||
Config.DeprecationWarnings.warn()
|
||||
Pleroma.Plugs.HTTPSecurityPlug.warn_if_disabled()
|
||||
Pleroma.ApplicationRequirements.verify!()
|
||||
|
|
|
@ -56,6 +56,7 @@ def warn do
|
|||
check_old_mrf_config()
|
||||
check_media_proxy_whitelist_config()
|
||||
check_welcome_message_config()
|
||||
check_gun_pool_options()
|
||||
end
|
||||
|
||||
def check_welcome_message_config do
|
||||
|
@ -115,4 +116,46 @@ def check_media_proxy_whitelist_config do
|
|||
""")
|
||||
end
|
||||
end
|
||||
|
||||
def check_gun_pool_options do
|
||||
pool_config = Config.get(:connections_pool)
|
||||
|
||||
if timeout = pool_config[:await_up_timeout] do
|
||||
Logger.warn("""
|
||||
!!!DEPRECATION WARNING!!!
|
||||
Your config is using old setting name `await_up_timeout` instead of `connect_timeout`. Setting should work for now, but you are advised to change format to scheme with port to prevent possible issues later.
|
||||
""")
|
||||
|
||||
Config.put(:connections_pool, Keyword.put_new(pool_config, :connect_timeout, timeout))
|
||||
end
|
||||
|
||||
pools_configs = Config.get(:pools)
|
||||
|
||||
warning_preface = """
|
||||
!!!DEPRECATION WARNING!!!
|
||||
Your config is using old setting name `timeout` instead of `recv_timeout` in pool settings. Setting should work for now, but you are advised to change format to scheme with port to prevent possible issues later.
|
||||
"""
|
||||
|
||||
updated_config =
|
||||
Enum.reduce(pools_configs, [], fn {pool_name, config}, acc ->
|
||||
if timeout = config[:timeout] do
|
||||
Keyword.put(acc, pool_name, Keyword.put_new(config, :recv_timeout, timeout))
|
||||
else
|
||||
acc
|
||||
end
|
||||
end)
|
||||
|
||||
if updated_config != [] do
|
||||
pool_warnings =
|
||||
updated_config
|
||||
|> Keyword.keys()
|
||||
|> Enum.map(fn pool_name ->
|
||||
"\n* `:timeout` options in #{pool_name} pool is now `:recv_timeout`"
|
||||
end)
|
||||
|
||||
Logger.warn(Enum.join([warning_preface | pool_warnings]))
|
||||
|
||||
Config.put(:pools, updated_config)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
30
lib/pleroma/config/oban.ex
Normal file
30
lib/pleroma/config/oban.ex
Normal file
|
@ -0,0 +1,30 @@
|
|||
defmodule Pleroma.Config.Oban do
|
||||
require Logger
|
||||
|
||||
def warn do
|
||||
oban_config = Pleroma.Config.get(Oban)
|
||||
|
||||
crontab =
|
||||
[Pleroma.Workers.Cron.StatsWorker]
|
||||
|> Enum.reduce(oban_config[:crontab], fn removed_worker, acc ->
|
||||
with acc when is_list(acc) <- acc,
|
||||
setting when is_tuple(setting) <-
|
||||
Enum.find(acc, fn {_, worker} -> worker == removed_worker end) do
|
||||
"""
|
||||
!!!OBAN CONFIG WARNING!!!
|
||||
You are using old workers in Oban crontab settings, which were removed.
|
||||
Please, remove setting from crontab in your config file (prod.secret.exs): #{
|
||||
inspect(setting)
|
||||
}
|
||||
"""
|
||||
|> Logger.warn()
|
||||
|
||||
List.delete(acc, setting)
|
||||
else
|
||||
_ -> acc
|
||||
end
|
||||
end)
|
||||
|
||||
Pleroma.Config.put(Oban, Keyword.put(oban_config, :crontab, crontab))
|
||||
end
|
||||
end
|
|
@ -13,7 +13,7 @@ def open(%URI{} = uri, opts) do
|
|||
opts =
|
||||
opts
|
||||
|> Enum.into(%{})
|
||||
|> Map.put_new(:await_up_timeout, pool_opts[:await_up_timeout] || 5_000)
|
||||
|> Map.put_new(:connect_timeout, pool_opts[:connect_timeout] || 5_000)
|
||||
|> Map.put_new(:supervise, false)
|
||||
|> maybe_add_tls_opts(uri)
|
||||
|
||||
|
@ -50,7 +50,7 @@ defp do_open(uri, %{proxy: {proxy_host, proxy_port}} = opts) do
|
|||
|
||||
with open_opts <- Map.delete(opts, :tls_opts),
|
||||
{:ok, conn} <- Gun.open(proxy_host, proxy_port, open_opts),
|
||||
{:ok, _} <- Gun.await_up(conn, opts[:await_up_timeout]),
|
||||
{:ok, _} <- Gun.await_up(conn, opts[:connect_timeout]),
|
||||
stream <- Gun.connect(conn, connect_opts),
|
||||
{:response, :fin, 200, _} <- Gun.await(conn, stream) do
|
||||
{:ok, conn}
|
||||
|
@ -88,7 +88,7 @@ defp do_open(uri, %{proxy: {proxy_type, proxy_host, proxy_port}} = opts) do
|
|||
|> Map.put(:socks_opts, socks_opts)
|
||||
|
||||
with {:ok, conn} <- Gun.open(proxy_host, proxy_port, opts),
|
||||
{:ok, _} <- Gun.await_up(conn, opts[:await_up_timeout]) do
|
||||
{:ok, _} <- Gun.await_up(conn, opts[:connect_timeout]) do
|
||||
{:ok, conn}
|
||||
else
|
||||
error ->
|
||||
|
@ -106,7 +106,7 @@ defp do_open(%URI{host: host, port: port} = uri, opts) do
|
|||
host = Pleroma.HTTP.AdapterHelper.parse_host(host)
|
||||
|
||||
with {:ok, conn} <- Gun.open(host, port, opts),
|
||||
{:ok, _} <- Gun.await_up(conn, opts[:await_up_timeout]) do
|
||||
{:ok, _} <- Gun.await_up(conn, opts[:connect_timeout]) do
|
||||
{:ok, conn}
|
||||
else
|
||||
error ->
|
||||
|
|
|
@ -100,21 +100,27 @@ defp generate_scrubber_signature(scrubbers) do
|
|||
end)
|
||||
end
|
||||
|
||||
def extract_first_external_url(_, nil), do: {:error, "No content"}
|
||||
def extract_first_external_url_from_object(%{data: %{"content" => content}} = object)
|
||||
when is_binary(content) do
|
||||
unless object.data["fake"] do
|
||||
key = "URL|#{object.id}"
|
||||
|
||||
def extract_first_external_url(object, content) do
|
||||
key = "URL|#{object.id}"
|
||||
Cachex.fetch!(:scrubber_cache, key, fn _key ->
|
||||
{:commit, {:ok, extract_first_external_url(content)}}
|
||||
end)
|
||||
else
|
||||
{:ok, extract_first_external_url(content)}
|
||||
end
|
||||
end
|
||||
|
||||
Cachex.fetch!(:scrubber_cache, key, fn _key ->
|
||||
result =
|
||||
content
|
||||
|> Floki.parse_fragment!()
|
||||
|> Floki.find("a:not(.mention,.hashtag,.attachment,[rel~=\"tag\"])")
|
||||
|> Enum.take(1)
|
||||
|> Floki.attribute("href")
|
||||
|> Enum.at(0)
|
||||
def extract_first_external_url_from_object(_), do: {:error, :no_content}
|
||||
|
||||
{:commit, {:ok, result}}
|
||||
end)
|
||||
def extract_first_external_url(content) do
|
||||
content
|
||||
|> Floki.parse_fragment!()
|
||||
|> Floki.find("a:not(.mention,.hashtag,.attachment,[rel~=\"tag\"])")
|
||||
|> Enum.take(1)
|
||||
|> Floki.attribute("href")
|
||||
|> Enum.at(0)
|
||||
end
|
||||
end
|
||||
|
|
|
@ -6,7 +6,7 @@ defmodule Pleroma.HTTP.AdapterHelper do
|
|||
@moduledoc """
|
||||
Configure Tesla.Client with default and customized adapter options.
|
||||
"""
|
||||
@defaults [pool: :federation]
|
||||
@defaults [pool: :federation, connect_timeout: 5_000, recv_timeout: 5_000]
|
||||
|
||||
@type proxy_type() :: :socks4 | :socks5
|
||||
@type host() :: charlist() | :inet.ip_address()
|
||||
|
|
|
@ -11,12 +11,8 @@ defmodule Pleroma.HTTP.AdapterHelper.Gun do
|
|||
require Logger
|
||||
|
||||
@defaults [
|
||||
connect_timeout: 5_000,
|
||||
domain_lookup_timeout: 5_000,
|
||||
tls_handshake_timeout: 5_000,
|
||||
retry: 1,
|
||||
retry_timeout: 1000,
|
||||
await_up_timeout: 5_000
|
||||
retry_timeout: 1_000
|
||||
]
|
||||
|
||||
@type pool() :: :federation | :upload | :media | :default
|
||||
|
@ -45,15 +41,17 @@ defp add_scheme_opts(opts, %{scheme: "https"}) do
|
|||
end
|
||||
|
||||
defp put_timeout(opts) do
|
||||
{recv_timeout, opts} = Keyword.pop(opts, :recv_timeout, pool_timeout(opts[:pool]))
|
||||
# this is the timeout to receive a message from Gun
|
||||
Keyword.put_new(opts, :timeout, pool_timeout(opts[:pool]))
|
||||
# `:timeout` key is used in Tesla
|
||||
Keyword.put(opts, :timeout, recv_timeout)
|
||||
end
|
||||
|
||||
@spec pool_timeout(pool()) :: non_neg_integer()
|
||||
def pool_timeout(pool) do
|
||||
default = Config.get([:pools, :default, :timeout], 5_000)
|
||||
default = Config.get([:pools, :default, :recv_timeout], 5_000)
|
||||
|
||||
Config.get([:pools, pool, :timeout], default)
|
||||
Config.get([:pools, pool, :recv_timeout], default)
|
||||
end
|
||||
|
||||
@prefix Pleroma.Gun.ConnectionPool
|
||||
|
|
|
@ -2,11 +2,8 @@ defmodule Pleroma.HTTP.AdapterHelper.Hackney do
|
|||
@behaviour Pleroma.HTTP.AdapterHelper
|
||||
|
||||
@defaults [
|
||||
connect_timeout: 10_000,
|
||||
recv_timeout: 20_000,
|
||||
follow_redirect: true,
|
||||
force_redirect: true,
|
||||
pool: :federation
|
||||
force_redirect: true
|
||||
]
|
||||
|
||||
@spec options(keyword(), URI.t()) :: keyword()
|
||||
|
@ -19,8 +16,21 @@ def options(connection_opts \\ [], %URI{} = uri) do
|
|||
|> Keyword.merge(config_opts)
|
||||
|> Keyword.merge(connection_opts)
|
||||
|> add_scheme_opts(uri)
|
||||
|> maybe_add_with_body()
|
||||
|> Pleroma.HTTP.AdapterHelper.maybe_add_proxy(proxy)
|
||||
end
|
||||
|
||||
defp add_scheme_opts(opts, %URI{scheme: "https"}) do
|
||||
Keyword.put(opts, :ssl_options, versions: [:"tlsv1.2", :"tlsv1.1", :tlsv1])
|
||||
end
|
||||
|
||||
defp add_scheme_opts(opts, _), do: opts
|
||||
|
||||
defp maybe_add_with_body(opts) do
|
||||
if opts[:max_body] do
|
||||
Keyword.put(opts, :with_body, true)
|
||||
else
|
||||
opts
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -11,7 +11,7 @@ defmodule Pleroma.HTTP.ExAws do
|
|||
|
||||
@impl true
|
||||
def request(method, url, body \\ "", headers \\ [], http_opts \\ []) do
|
||||
http_opts = Keyword.put_new(http_opts, :adapter, pool: :upload)
|
||||
http_opts = Keyword.put_new(http_opts, :pool, :upload)
|
||||
|
||||
case HTTP.request(method, url, body, headers, http_opts) do
|
||||
{:ok, env} ->
|
||||
|
|
|
@ -60,7 +60,7 @@ def post(url, body, headers \\ [], options \\ []),
|
|||
{:ok, Env.t()} | {:error, any()}
|
||||
def request(method, url, body, headers, options) when is_binary(url) do
|
||||
uri = URI.parse(url)
|
||||
adapter_opts = AdapterHelper.options(uri, options[:adapter] || [])
|
||||
adapter_opts = AdapterHelper.options(uri, options || [])
|
||||
|
||||
options = put_in(options[:adapter], adapter_opts)
|
||||
params = options[:params] || []
|
||||
|
|
|
@ -11,7 +11,7 @@ defmodule Pleroma.HTTP.Tzdata do
|
|||
|
||||
@impl true
|
||||
def get(url, headers, options) do
|
||||
options = Keyword.put_new(options, :adapter, pool: :default)
|
||||
options = Keyword.put_new(options, :pool, :default)
|
||||
|
||||
with {:ok, %Tesla.Env{} = env} <- HTTP.get(url, headers, options) do
|
||||
{:ok, {env.status, env.headers, env.body}}
|
||||
|
@ -20,7 +20,7 @@ def get(url, headers, options) do
|
|||
|
||||
@impl true
|
||||
def head(url, headers, options) do
|
||||
options = Keyword.put_new(options, :adapter, pool: :default)
|
||||
options = Keyword.put_new(options, :pool, :default)
|
||||
|
||||
with {:ok, %Tesla.Env{} = env} <- HTTP.head(url, headers, options) do
|
||||
{:ok, {env.status, env.headers}}
|
||||
|
|
|
@ -14,6 +14,8 @@ defmodule Pleroma.Instances.Instance do
|
|||
import Ecto.Query
|
||||
import Ecto.Changeset
|
||||
|
||||
require Logger
|
||||
|
||||
schema "instances" do
|
||||
field(:host, :string)
|
||||
field(:unreachable_since, :naive_datetime_usec)
|
||||
|
@ -145,6 +147,10 @@ def get_or_update_favicon(%URI{host: host} = instance_uri) do
|
|||
|
||||
favicon
|
||||
end
|
||||
rescue
|
||||
e ->
|
||||
Logger.warn("Instance.get_or_update_favicon(\"#{host}\") error: #{inspect(e)}")
|
||||
nil
|
||||
end
|
||||
|
||||
defp scrape_favicon(%URI{} = instance_uri) do
|
||||
|
@ -165,7 +171,12 @@ defp scrape_favicon(%URI{} = instance_uri) do
|
|||
_ -> nil
|
||||
end
|
||||
rescue
|
||||
_ -> nil
|
||||
e ->
|
||||
Logger.warn(
|
||||
"Instance.scrape_favicon(\"#{to_string(instance_uri)}\") error: #{inspect(e)}"
|
||||
)
|
||||
|
||||
nil
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -7,6 +7,7 @@ defmodule Pleroma.ReverseProxy.Client.Hackney do
|
|||
|
||||
@impl true
|
||||
def request(method, url, headers, body, opts \\ []) do
|
||||
opts = Keyword.put(opts, :ssl_options, versions: [:"tlsv1.2", :"tlsv1.1", :tlsv1])
|
||||
:hackney.request(method, url, headers, body, opts)
|
||||
end
|
||||
|
||||
|
|
|
@ -3,12 +3,15 @@
|
|||
# SPDX-License-Identifier: AGPL-3.0-only
|
||||
|
||||
defmodule Pleroma.Stats do
|
||||
use GenServer
|
||||
|
||||
import Ecto.Query
|
||||
|
||||
alias Pleroma.CounterCache
|
||||
alias Pleroma.Repo
|
||||
alias Pleroma.User
|
||||
|
||||
use GenServer
|
||||
@interval :timer.seconds(60)
|
||||
|
||||
def start_link(_) do
|
||||
GenServer.start_link(
|
||||
|
@ -18,6 +21,12 @@ def start_link(_) do
|
|||
)
|
||||
end
|
||||
|
||||
@impl true
|
||||
def init(_args) do
|
||||
if Pleroma.Config.get(:env) == :test, do: :ok = Ecto.Adapters.SQL.Sandbox.checkout(Repo)
|
||||
{:ok, nil, {:continue, :calculate_stats}}
|
||||
end
|
||||
|
||||
@doc "Performs update stats"
|
||||
def force_update do
|
||||
GenServer.call(__MODULE__, :force_update)
|
||||
|
@ -29,7 +38,11 @@ def do_collect do
|
|||
end
|
||||
|
||||
@doc "Returns stats data"
|
||||
@spec get_stats() :: %{domain_count: integer(), status_count: integer(), user_count: integer()}
|
||||
@spec get_stats() :: %{
|
||||
domain_count: non_neg_integer(),
|
||||
status_count: non_neg_integer(),
|
||||
user_count: non_neg_integer()
|
||||
}
|
||||
def get_stats do
|
||||
%{stats: stats} = GenServer.call(__MODULE__, :get_state)
|
||||
|
||||
|
@ -44,25 +57,14 @@ def get_peers do
|
|||
peers
|
||||
end
|
||||
|
||||
def init(_args) do
|
||||
{:ok, calculate_stat_data()}
|
||||
end
|
||||
|
||||
def handle_call(:force_update, _from, _state) do
|
||||
new_stats = calculate_stat_data()
|
||||
{:reply, new_stats, new_stats}
|
||||
end
|
||||
|
||||
def handle_call(:get_state, _from, state) do
|
||||
{:reply, state, state}
|
||||
end
|
||||
|
||||
def handle_cast(:run_update, _state) do
|
||||
new_stats = calculate_stat_data()
|
||||
|
||||
{:noreply, new_stats}
|
||||
end
|
||||
|
||||
@spec calculate_stat_data() :: %{
|
||||
peers: list(),
|
||||
stats: %{
|
||||
domain_count: non_neg_integer(),
|
||||
status_count: non_neg_integer(),
|
||||
user_count: non_neg_integer()
|
||||
}
|
||||
}
|
||||
def calculate_stat_data do
|
||||
peers =
|
||||
from(
|
||||
|
@ -97,6 +99,7 @@ def calculate_stat_data do
|
|||
}
|
||||
end
|
||||
|
||||
@spec get_status_visibility_count(String.t() | nil) :: map()
|
||||
def get_status_visibility_count(instance \\ nil) do
|
||||
if is_nil(instance) do
|
||||
CounterCache.get_sum()
|
||||
|
@ -104,4 +107,36 @@ def get_status_visibility_count(instance \\ nil) do
|
|||
CounterCache.get_by_instance(instance)
|
||||
end
|
||||
end
|
||||
|
||||
@impl true
|
||||
def handle_continue(:calculate_stats, _) do
|
||||
stats = calculate_stat_data()
|
||||
Process.send_after(self(), :run_update, @interval)
|
||||
{:noreply, stats}
|
||||
end
|
||||
|
||||
@impl true
|
||||
def handle_call(:force_update, _from, _state) do
|
||||
new_stats = calculate_stat_data()
|
||||
{:reply, new_stats, new_stats}
|
||||
end
|
||||
|
||||
@impl true
|
||||
def handle_call(:get_state, _from, state) do
|
||||
{:reply, state, state}
|
||||
end
|
||||
|
||||
@impl true
|
||||
def handle_cast(:run_update, _state) do
|
||||
new_stats = calculate_stat_data()
|
||||
|
||||
{:noreply, new_stats}
|
||||
end
|
||||
|
||||
@impl true
|
||||
def handle_info(:run_update, _) do
|
||||
new_stats = calculate_stat_data()
|
||||
Process.send_after(self(), :run_update, @interval)
|
||||
{:noreply, new_stats}
|
||||
end
|
||||
end
|
||||
|
|
|
@ -15,7 +15,11 @@ defmodule Pleroma.Upload.Filter do
|
|||
|
||||
require Logger
|
||||
|
||||
@callback filter(Pleroma.Upload.t()) :: :ok | {:ok, Pleroma.Upload.t()} | {:error, any()}
|
||||
@callback filter(Pleroma.Upload.t()) ::
|
||||
{:ok, :filtered}
|
||||
| {:ok, :noop}
|
||||
| {:ok, :filtered, Pleroma.Upload.t()}
|
||||
| {:error, any()}
|
||||
|
||||
@spec filter([module()], Pleroma.Upload.t()) :: {:ok, Pleroma.Upload.t()} | {:error, any()}
|
||||
|
||||
|
@ -25,10 +29,13 @@ def filter([], upload) do
|
|||
|
||||
def filter([filter | rest], upload) do
|
||||
case filter.filter(upload) do
|
||||
:ok ->
|
||||
{:ok, :filtered} ->
|
||||
filter(rest, upload)
|
||||
|
||||
{:ok, upload} ->
|
||||
{:ok, :filtered, upload} ->
|
||||
filter(rest, upload)
|
||||
|
||||
{:ok, :noop} ->
|
||||
filter(rest, upload)
|
||||
|
||||
error ->
|
||||
|
|
|
@ -16,9 +16,11 @@ defmodule Pleroma.Upload.Filter.AnonymizeFilename do
|
|||
def filter(%Upload{name: name} = upload) do
|
||||
extension = List.last(String.split(name, "."))
|
||||
name = predefined_name(extension) || random(extension)
|
||||
{:ok, %Upload{upload | name: name}}
|
||||
{:ok, :filtered, %Upload{upload | name: name}}
|
||||
end
|
||||
|
||||
def filter(_), do: {:ok, :noop}
|
||||
|
||||
@spec predefined_name(String.t()) :: String.t() | nil
|
||||
defp predefined_name(extension) do
|
||||
with name when not is_nil(name) <- Config.get([__MODULE__, :text]),
|
||||
|
|
|
@ -17,8 +17,8 @@ def filter(%Upload{name: name, tempfile: tempfile} = upload) do
|
|||
|> Base.encode16(case: :lower)
|
||||
|
||||
filename = shasum <> "." <> extension
|
||||
{:ok, %Upload{upload | id: shasum, path: filename}}
|
||||
{:ok, :filtered, %Upload{upload | id: shasum, path: filename}}
|
||||
end
|
||||
|
||||
def filter(_), do: :ok
|
||||
def filter(_), do: {:ok, :noop}
|
||||
end
|
||||
|
|
|
@ -9,11 +9,15 @@ defmodule Pleroma.Upload.Filter.Exiftool do
|
|||
"""
|
||||
@behaviour Pleroma.Upload.Filter
|
||||
|
||||
@spec filter(Pleroma.Upload.t()) :: :ok | {:error, String.t()}
|
||||
@spec filter(Pleroma.Upload.t()) :: {:ok, any()} | {:error, String.t()}
|
||||
|
||||
# webp is not compatible with exiftool at this time
|
||||
def filter(%Pleroma.Upload{content_type: "image/webp"}), do: {:ok, :noop}
|
||||
|
||||
def filter(%Pleroma.Upload{tempfile: file, content_type: "image" <> _}) do
|
||||
try do
|
||||
case System.cmd("exiftool", ["-overwrite_original", "-gps:all=", file], parallelism: true) do
|
||||
{_response, 0} -> :ok
|
||||
{_response, 0} -> {:ok, :filtered}
|
||||
{error, 1} -> {:error, error}
|
||||
end
|
||||
rescue
|
||||
|
@ -22,5 +26,5 @@ def filter(%Pleroma.Upload{tempfile: file, content_type: "image" <> _}) do
|
|||
end
|
||||
end
|
||||
|
||||
def filter(_), do: :ok
|
||||
def filter(_), do: {:ok, :noop}
|
||||
end
|
||||
|
|
|
@ -38,16 +38,16 @@ defmodule Pleroma.Upload.Filter.Mogrifun do
|
|||
[{"fill", "yellow"}, {"tint", "40"}]
|
||||
]
|
||||
|
||||
@spec filter(Pleroma.Upload.t()) :: :ok | {:error, String.t()}
|
||||
@spec filter(Pleroma.Upload.t()) :: {:ok, atom()} | {:error, String.t()}
|
||||
def filter(%Pleroma.Upload{tempfile: file, content_type: "image" <> _}) do
|
||||
try do
|
||||
Filter.Mogrify.do_filter(file, [Enum.random(@filters)])
|
||||
:ok
|
||||
{:ok, :filtered}
|
||||
rescue
|
||||
_e in ErlangError ->
|
||||
{:error, "mogrify command not found"}
|
||||
end
|
||||
end
|
||||
|
||||
def filter(_), do: :ok
|
||||
def filter(_), do: {:ok, :noop}
|
||||
end
|
||||
|
|
|
@ -8,18 +8,18 @@ defmodule Pleroma.Upload.Filter.Mogrify do
|
|||
@type conversion :: action :: String.t() | {action :: String.t(), opts :: String.t()}
|
||||
@type conversions :: conversion() | [conversion()]
|
||||
|
||||
@spec filter(Pleroma.Upload.t()) :: :ok | {:error, String.t()}
|
||||
@spec filter(Pleroma.Upload.t()) :: {:ok, :atom} | {:error, String.t()}
|
||||
def filter(%Pleroma.Upload{tempfile: file, content_type: "image" <> _}) do
|
||||
try do
|
||||
do_filter(file, Pleroma.Config.get!([__MODULE__, :args]))
|
||||
:ok
|
||||
{:ok, :filtered}
|
||||
rescue
|
||||
_e in ErlangError ->
|
||||
{:error, "mogrify command not found"}
|
||||
end
|
||||
end
|
||||
|
||||
def filter(_), do: :ok
|
||||
def filter(_), do: {:ok, :noop}
|
||||
|
||||
def do_filter(file, filters) do
|
||||
file
|
||||
|
|
|
@ -1125,31 +1125,31 @@ def get_followers_query(%User{} = user, nil) do
|
|||
User.Query.build(%{followers: user, deactivated: false})
|
||||
end
|
||||
|
||||
def get_followers_query(user, page) do
|
||||
def get_followers_query(%User{} = user, page) do
|
||||
user
|
||||
|> get_followers_query(nil)
|
||||
|> User.Query.paginate(page, 20)
|
||||
end
|
||||
|
||||
@spec get_followers_query(User.t()) :: Ecto.Query.t()
|
||||
def get_followers_query(user), do: get_followers_query(user, nil)
|
||||
def get_followers_query(%User{} = user), do: get_followers_query(user, nil)
|
||||
|
||||
@spec get_followers(User.t(), pos_integer() | nil) :: {:ok, list(User.t())}
|
||||
def get_followers(user, page \\ nil) do
|
||||
def get_followers(%User{} = user, page \\ nil) do
|
||||
user
|
||||
|> get_followers_query(page)
|
||||
|> Repo.all()
|
||||
end
|
||||
|
||||
@spec get_external_followers(User.t(), pos_integer() | nil) :: {:ok, list(User.t())}
|
||||
def get_external_followers(user, page \\ nil) do
|
||||
def get_external_followers(%User{} = user, page \\ nil) do
|
||||
user
|
||||
|> get_followers_query(page)
|
||||
|> User.Query.build(%{external: true})
|
||||
|> Repo.all()
|
||||
end
|
||||
|
||||
def get_followers_ids(user, page \\ nil) do
|
||||
def get_followers_ids(%User{} = user, page \\ nil) do
|
||||
user
|
||||
|> get_followers_query(page)
|
||||
|> select([u], u.id)
|
||||
|
@ -1161,29 +1161,29 @@ def get_friends_query(%User{} = user, nil) do
|
|||
User.Query.build(%{friends: user, deactivated: false})
|
||||
end
|
||||
|
||||
def get_friends_query(user, page) do
|
||||
def get_friends_query(%User{} = user, page) do
|
||||
user
|
||||
|> get_friends_query(nil)
|
||||
|> User.Query.paginate(page, 20)
|
||||
end
|
||||
|
||||
@spec get_friends_query(User.t()) :: Ecto.Query.t()
|
||||
def get_friends_query(user), do: get_friends_query(user, nil)
|
||||
def get_friends_query(%User{} = user), do: get_friends_query(user, nil)
|
||||
|
||||
def get_friends(user, page \\ nil) do
|
||||
def get_friends(%User{} = user, page \\ nil) do
|
||||
user
|
||||
|> get_friends_query(page)
|
||||
|> Repo.all()
|
||||
end
|
||||
|
||||
def get_friends_ap_ids(user) do
|
||||
def get_friends_ap_ids(%User{} = user) do
|
||||
user
|
||||
|> get_friends_query(nil)
|
||||
|> select([u], u.ap_id)
|
||||
|> Repo.all()
|
||||
end
|
||||
|
||||
def get_friends_ids(user, page \\ nil) do
|
||||
def get_friends_ids(%User{} = user, page \\ nil) do
|
||||
user
|
||||
|> get_friends_query(page)
|
||||
|> select([u], u.id)
|
||||
|
|
|
@ -115,8 +115,8 @@ defp trigram_rank(query, query_string) do
|
|||
)
|
||||
end
|
||||
|
||||
defp base_query(_user, false), do: User
|
||||
defp base_query(user, true), do: User.get_friends_query(user)
|
||||
defp base_query(%User{} = user, true), do: User.get_friends_query(user)
|
||||
defp base_query(_user, _following), do: User
|
||||
|
||||
defp filter_invisible_users(query) do
|
||||
from(q in query, where: q.invisible == false)
|
||||
|
|
|
@ -399,21 +399,30 @@ def read_inbox(%{assigns: %{user: %User{nickname: as_nickname}}} = conn, %{
|
|||
|
||||
defp handle_user_activity(
|
||||
%User{} = user,
|
||||
%{"type" => "Create", "object" => %{"type" => "Note"}} = params
|
||||
%{"type" => "Create", "object" => %{"type" => "Note"} = object} = params
|
||||
) do
|
||||
object =
|
||||
params["object"]
|
||||
|> Map.merge(Map.take(params, ["to", "cc"]))
|
||||
|> Map.put("attributedTo", user.ap_id())
|
||||
|> Transmogrifier.fix_object()
|
||||
content = if is_binary(object["content"]), do: object["content"], else: ""
|
||||
name = if is_binary(object["name"]), do: object["name"], else: ""
|
||||
summary = if is_binary(object["summary"]), do: object["summary"], else: ""
|
||||
length = String.length(content <> name <> summary)
|
||||
|
||||
ActivityPub.create(%{
|
||||
to: params["to"],
|
||||
actor: user,
|
||||
context: object["context"],
|
||||
object: object,
|
||||
additional: Map.take(params, ["cc"])
|
||||
})
|
||||
if length > Pleroma.Config.get([:instance, :limit]) do
|
||||
{:error, dgettext("errors", "Note is over the character limit")}
|
||||
else
|
||||
object =
|
||||
object
|
||||
|> Map.merge(Map.take(params, ["to", "cc"]))
|
||||
|> Map.put("attributedTo", user.ap_id())
|
||||
|> Transmogrifier.fix_object()
|
||||
|
||||
ActivityPub.create(%{
|
||||
to: params["to"],
|
||||
actor: user,
|
||||
context: object["context"],
|
||||
object: object,
|
||||
additional: Map.take(params, ["cc"])
|
||||
})
|
||||
end
|
||||
end
|
||||
|
||||
defp handle_user_activity(%User{} = user, %{"type" => "Delete"} = params) do
|
||||
|
|
|
@ -0,0 +1,56 @@
|
|||
# Pleroma: A lightweight social networking server
|
||||
# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
|
||||
# SPDX-License-Identifier: AGPL-3.0-only
|
||||
|
||||
defmodule Pleroma.Web.ActivityPub.MRF.ForceBotUnlistedPolicy do
|
||||
alias Pleroma.User
|
||||
@behaviour Pleroma.Web.ActivityPub.MRF
|
||||
@moduledoc "Remove bot posts from federated timeline"
|
||||
|
||||
require Pleroma.Constants
|
||||
|
||||
defp check_by_actor_type(user), do: user.actor_type in ["Application", "Service"]
|
||||
defp check_by_nickname(user), do: Regex.match?(~r/bot@|ebooks@/i, user.nickname)
|
||||
|
||||
defp check_if_bot(user), do: check_by_actor_type(user) or check_by_nickname(user)
|
||||
|
||||
@impl true
|
||||
def filter(
|
||||
%{
|
||||
"type" => "Create",
|
||||
"to" => to,
|
||||
"cc" => cc,
|
||||
"actor" => actor,
|
||||
"object" => object
|
||||
} = message
|
||||
) do
|
||||
user = User.get_cached_by_ap_id(actor)
|
||||
isbot = check_if_bot(user)
|
||||
|
||||
if isbot and Enum.member?(to, Pleroma.Constants.as_public()) do
|
||||
to = List.delete(to, Pleroma.Constants.as_public()) ++ [user.follower_address]
|
||||
cc = List.delete(cc, user.follower_address) ++ [Pleroma.Constants.as_public()]
|
||||
|
||||
object =
|
||||
object
|
||||
|> Map.put("to", to)
|
||||
|> Map.put("cc", cc)
|
||||
|
||||
message =
|
||||
message
|
||||
|> Map.put("to", to)
|
||||
|> Map.put("cc", cc)
|
||||
|> Map.put("object", object)
|
||||
|
||||
{:ok, message}
|
||||
else
|
||||
{:ok, message}
|
||||
end
|
||||
end
|
||||
|
||||
@impl true
|
||||
def filter(message), do: {:ok, message}
|
||||
|
||||
@impl true
|
||||
def describe, do: {:ok, %{}}
|
||||
end
|
|
@ -13,22 +13,16 @@ defmodule Pleroma.Web.ActivityPub.MRF.MediaProxyWarmingPolicy do
|
|||
require Logger
|
||||
|
||||
@options [
|
||||
pool: :media
|
||||
pool: :media,
|
||||
recv_timeout: 10_000
|
||||
]
|
||||
|
||||
def perform(:prefetch, url) do
|
||||
Logger.debug("Prefetching #{inspect(url)}")
|
||||
|
||||
opts =
|
||||
if Application.get_env(:tesla, :adapter) == Tesla.Adapter.Hackney do
|
||||
Keyword.put(@options, :recv_timeout, 10_000)
|
||||
else
|
||||
@options
|
||||
end
|
||||
|
||||
url
|
||||
|> MediaProxy.url()
|
||||
|> HTTP.get([], adapter: opts)
|
||||
|> HTTP.get([], @options)
|
||||
end
|
||||
|
||||
def perform(:preload, %{"object" => %{"attachment" => attachments}} = _message) do
|
||||
|
|
|
@ -379,8 +379,7 @@ defp maybe_parse_filters(filters) do
|
|||
filters
|
||||
|> String.split(",")
|
||||
|> Enum.filter(&Enum.member?(@filters, &1))
|
||||
|> Enum.map(&String.to_atom/1)
|
||||
|> Map.new(&{&1, true})
|
||||
|> Map.new(&{String.to_existing_atom(&1), true})
|
||||
end
|
||||
|
||||
def right_add_multiple(%{assigns: %{user: admin}} = conn, %{
|
||||
|
|
|
@ -9,7 +9,15 @@ defmodule Pleroma.Web.Feed.TagController do
|
|||
alias Pleroma.Web.ActivityPub.ActivityPub
|
||||
alias Pleroma.Web.Feed.FeedView
|
||||
|
||||
def feed(conn, %{"tag" => raw_tag} = params) do
|
||||
def feed(conn, params) do
|
||||
unless Pleroma.Config.restrict_unauthenticated_access?(:activities, :local) do
|
||||
render_feed(conn, params)
|
||||
else
|
||||
render_error(conn, :not_found, "Not found")
|
||||
end
|
||||
end
|
||||
|
||||
def render_feed(conn, %{"tag" => raw_tag} = params) do
|
||||
{format, tag} = parse_tag(raw_tag)
|
||||
|
||||
activities =
|
||||
|
|
|
@ -37,7 +37,15 @@ def feed_redirect(conn, %{"nickname" => nickname}) do
|
|||
end
|
||||
end
|
||||
|
||||
def feed(conn, %{"nickname" => nickname} = params) do
|
||||
def feed(conn, params) do
|
||||
unless Pleroma.Config.restrict_unauthenticated_access?(:profiles, :local) do
|
||||
render_feed(conn, params)
|
||||
else
|
||||
errors(conn, {:error, :not_found})
|
||||
end
|
||||
end
|
||||
|
||||
def render_feed(conn, %{"nickname" => nickname} = params) do
|
||||
format = get_format(conn)
|
||||
|
||||
format =
|
||||
|
|
|
@ -7,8 +7,9 @@ defmodule Pleroma.Web.Metadata do
|
|||
|
||||
def build_tags(params) do
|
||||
providers = [
|
||||
Pleroma.Web.Metadata.Providers.RelMe,
|
||||
Pleroma.Web.Metadata.Providers.RestrictIndexing
|
||||
| Pleroma.Config.get([__MODULE__, :providers], [])
|
||||
| activated_providers()
|
||||
]
|
||||
|
||||
Enum.reduce(providers, "", fn parser, acc ->
|
||||
|
@ -42,4 +43,12 @@ def activity_nsfw?(%{data: %{"sensitive" => sensitive}}) do
|
|||
def activity_nsfw?(_) do
|
||||
false
|
||||
end
|
||||
|
||||
defp activated_providers do
|
||||
unless Pleroma.Config.restrict_unauthenticated_access?(:activities, :local) do
|
||||
[Pleroma.Web.Metadata.Providers.Feed | Pleroma.Config.get([__MODULE__, :providers], [])]
|
||||
else
|
||||
[]
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -5,7 +5,8 @@
|
|||
defmodule Pleroma.Web.RelMe do
|
||||
@options [
|
||||
pool: :media,
|
||||
max_body: 2_000_000
|
||||
max_body: 2_000_000,
|
||||
recv_timeout: 2_000
|
||||
]
|
||||
|
||||
if Pleroma.Config.get(:env) == :test do
|
||||
|
@ -23,18 +24,8 @@ def parse(url) when is_binary(url) do
|
|||
def parse(_), do: {:error, "No URL provided"}
|
||||
|
||||
defp parse_url(url) do
|
||||
opts =
|
||||
if Application.get_env(:tesla, :adapter) == Tesla.Adapter.Hackney do
|
||||
Keyword.merge(@options,
|
||||
recv_timeout: 2_000,
|
||||
with_body: true
|
||||
)
|
||||
else
|
||||
@options
|
||||
end
|
||||
|
||||
with {:ok, %Tesla.Env{body: html, status: status}} when status in 200..299 <-
|
||||
Pleroma.HTTP.get(url, [], adapter: opts),
|
||||
Pleroma.HTTP.get(url, [], @options),
|
||||
{:ok, html_tree} <- Floki.parse_document(html),
|
||||
data <-
|
||||
Floki.attribute(html_tree, "link[rel~=me]", "href") ++
|
||||
|
|
|
@ -9,14 +9,15 @@ defmodule Pleroma.Web.RichMedia.Helpers do
|
|||
alias Pleroma.Object
|
||||
alias Pleroma.Web.RichMedia.Parser
|
||||
|
||||
@rich_media_options [
|
||||
@options [
|
||||
pool: :media,
|
||||
max_body: 2_000_000
|
||||
max_body: 2_000_000,
|
||||
recv_timeout: 2_000
|
||||
]
|
||||
|
||||
@spec validate_page_url(URI.t() | binary()) :: :ok | :error
|
||||
defp validate_page_url(page_url) when is_binary(page_url) do
|
||||
validate_tld = Pleroma.Config.get([Pleroma.Formatter, :validate_tld])
|
||||
validate_tld = Config.get([Pleroma.Formatter, :validate_tld])
|
||||
|
||||
page_url
|
||||
|> Linkify.Parser.url?(validate_tld: validate_tld)
|
||||
|
@ -58,7 +59,7 @@ def fetch_data_for_object(object) do
|
|||
with true <- Config.get([:rich_media, :enabled]),
|
||||
false <- object.data["sensitive"] || false,
|
||||
{:ok, page_url} <-
|
||||
HTML.extract_first_external_url(object, object.data["content"]),
|
||||
HTML.extract_first_external_url_from_object(object),
|
||||
:ok <- validate_page_url(page_url),
|
||||
{:ok, rich_media} <- Parser.parse(page_url) do
|
||||
%{page_url: page_url, rich_media: rich_media}
|
||||
|
@ -86,16 +87,6 @@ def perform(:fetch, %Activity{} = activity) do
|
|||
def rich_media_get(url) do
|
||||
headers = [{"user-agent", Pleroma.Application.user_agent() <> "; Bot"}]
|
||||
|
||||
options =
|
||||
if Application.get_env(:tesla, :adapter) == Tesla.Adapter.Hackney do
|
||||
Keyword.merge(@rich_media_options,
|
||||
recv_timeout: 2_000,
|
||||
with_body: true
|
||||
)
|
||||
else
|
||||
@rich_media_options
|
||||
end
|
||||
|
||||
Pleroma.HTTP.get(url, headers, adapter: options)
|
||||
Pleroma.HTTP.get(url, headers, @options)
|
||||
end
|
||||
end
|
||||
|
|
|
@ -1,17 +0,0 @@
|
|||
# Pleroma: A lightweight social networking server
|
||||
# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
|
||||
# SPDX-License-Identifier: AGPL-3.0-only
|
||||
|
||||
defmodule Pleroma.Workers.Cron.StatsWorker do
|
||||
@moduledoc """
|
||||
The worker to update peers statistics.
|
||||
"""
|
||||
|
||||
use Oban.Worker, queue: "background"
|
||||
|
||||
@impl Oban.Worker
|
||||
def perform(_job) do
|
||||
Pleroma.Stats.do_collect()
|
||||
:ok
|
||||
end
|
||||
end
|
8
mix.exs
8
mix.exs
|
@ -134,8 +134,8 @@ defp deps do
|
|||
{:cachex, "~> 3.2"},
|
||||
{:poison, "~> 3.0", override: true},
|
||||
{:tesla,
|
||||
git: "https://git.pleroma.social/pleroma/elixir-libraries/tesla.git",
|
||||
ref: "3a2789d8535f7b520ebbadc4494227e5ba0e5365",
|
||||
git: "https://github.com/teamon/tesla/",
|
||||
ref: "9f7261ca49f9f901ceb73b60219ad6f8a9f6aa30",
|
||||
override: true},
|
||||
{:castore, "~> 0.1"},
|
||||
{:cowlib, "~> 2.9", override: true},
|
||||
|
@ -197,7 +197,9 @@ defp deps do
|
|||
{:ex_machina, "~> 2.4", only: :test},
|
||||
{:credo, "~> 1.4", only: [:dev, :test], runtime: false},
|
||||
{:mock, "~> 0.3.5", only: :test},
|
||||
{:excoveralls, "~> 0.13.1", only: :test},
|
||||
# temporary downgrade for excoveralls, hackney until hackney max_connections bug will be fixed
|
||||
{:excoveralls, "0.12.3", only: :test},
|
||||
{:hackney, "1.15.2", override: true},
|
||||
{:mox, "~> 0.5", only: :test},
|
||||
{:websocket_client, git: "https://github.com/jeremyong/websocket_client.git", only: :test}
|
||||
] ++ oauth_deps()
|
||||
|
|
16
mix.lock
16
mix.lock
|
@ -11,7 +11,7 @@
|
|||
"calendar": {:hex, :calendar, "1.0.0", "f52073a708528482ec33d0a171954ca610fe2bd28f1e871f247dc7f1565fa807", [:mix], [{:tzdata, "~> 0.5.20 or ~> 0.1.201603 or ~> 1.0", [hex: :tzdata, repo: "hexpm", optional: false]}], "hexpm", "990e9581920c82912a5ee50e62ff5ef96da6b15949a2ee4734f935fdef0f0a6f"},
|
||||
"captcha": {:git, "https://git.pleroma.social/pleroma/elixir-libraries/elixir-captcha.git", "e0f16822d578866e186a0974d65ad58cddc1e2ab", [ref: "e0f16822d578866e186a0974d65ad58cddc1e2ab"]},
|
||||
"castore": {:hex, :castore, "0.1.7", "1ca19eee705cde48c9e809e37fdd0730510752cc397745e550f6065a56a701e9", [:mix], [], "hexpm", "a2ae2c13d40e9c308387f1aceb14786dca019ebc2a11484fb2a9f797ea0aa0d8"},
|
||||
"certifi": {:hex, :certifi, "2.5.2", "b7cfeae9d2ed395695dd8201c57a2d019c0c43ecaf8b8bcb9320b40d6662f340", [:rebar3], [{:parse_trans, "~>3.3", [hex: :parse_trans, repo: "hexpm", optional: false]}], "hexpm", "3b3b5f36493004ac3455966991eaf6e768ce9884693d9968055aeeeb1e575040"},
|
||||
"certifi": {:hex, :certifi, "2.5.1", "867ce347f7c7d78563450a18a6a28a8090331e77fa02380b4a21962a65d36ee5", [:rebar3], [{:parse_trans, "~>3.3", [hex: :parse_trans, repo: "hexpm", optional: false]}], "hexpm", "805abd97539caf89ec6d4732c91e62ba9da0cda51ac462380bbd28ee697a8c42"},
|
||||
"combine": {:hex, :combine, "0.10.0", "eff8224eeb56498a2af13011d142c5e7997a80c8f5b97c499f84c841032e429f", [:mix], [], "hexpm", "1b1dbc1790073076580d0d1d64e42eae2366583e7aecd455d1215b0d16f2451b"},
|
||||
"comeonin": {:hex, :comeonin, "5.3.1", "7fe612b739c78c9c1a75186ef2d322ce4d25032d119823269d0aa1e2f1e20025", [:mix], [], "hexpm", "d6222483060c17f0977fad1b7401ef0c5863c985a64352755f366aee3799c245"},
|
||||
"concurrent_limiter": {:git, "https://git.pleroma.social/pleroma/elixir-libraries/concurrent_limiter.git", "55e92f84b4ed531bd487952a71040a9c69dc2807", [ref: "55e92f84b4ed531bd487952a71040a9c69dc2807"]},
|
||||
|
@ -41,7 +41,7 @@
|
|||
"ex_doc": {:hex, :ex_doc, "0.22.2", "03a2a58bdd2ba0d83d004507c4ee113b9c521956938298eba16e55cc4aba4a6c", [:mix], [{:earmark_parser, "~> 1.4.0", [hex: :earmark_parser, repo: "hexpm", optional: false]}, {:makeup_elixir, "~> 0.14", [hex: :makeup_elixir, repo: "hexpm", optional: false]}], "hexpm", "cf60e1b3e2efe317095b6bb79651f83a2c1b3edcb4d319c421d7fcda8b3aff26"},
|
||||
"ex_machina": {:hex, :ex_machina, "2.4.0", "09a34c5d371bfb5f78399029194a8ff67aff340ebe8ba19040181af35315eabb", [: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", "a20bc9ddc721b33ea913b93666c5d0bdca5cbad7a67540784ae277228832d72c"},
|
||||
"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.13.1", "b9f1697f7c9e0cfe15d1a1d737fb169c398803ffcbc57e672aa007e9fd42864c", [:mix], [{:hackney, "~> 1.16", [hex: :hackney, repo: "hexpm", optional: false]}, {:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: false]}], "hexpm", "b4bb550e045def1b4d531a37fb766cbbe1307f7628bf8f0414168b3f52021cce"},
|
||||
"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.4", "4910ee49f2f6b19692e3bf30bf97f1b6b7dac489cd6b0f34cd0fe3042c56ba30", [:make, :mix], [{:elixir_make, "~> 0.4", [hex: :elixir_make, repo: "hexpm", optional: false]}, {:nimble_pool, "~> 0.1.0", [hex: :nimble_pool, repo: "hexpm", optional: false]}], "hexpm", "3bb49d541dfc02ad5e425904f53376d758c09f89e521afc7d2b174b3227761ea"},
|
||||
"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"},
|
||||
"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"},
|
||||
|
@ -51,12 +51,12 @@
|
|||
"gen_state_machine": {:hex, :gen_state_machine, "2.0.5", "9ac15ec6e66acac994cc442dcc2c6f9796cf380ec4b08267223014be1c728a95", [:mix], [], "hexpm"},
|
||||
"gettext": {:hex, :gettext, "0.18.0", "406d6b9e0e3278162c2ae1de0a60270452c553536772167e2d701f028116f870", [:mix], [], "hexpm", "c3f850be6367ebe1a08616c2158affe4a23231c70391050bf359d5f92f66a571"},
|
||||
"gun": {:git, "https://github.com/ninenines/gun.git", "921c47146b2d9567eac7e9a4d2ccc60fffd4f327", [ref: "921c47146b2d9567eac7e9a4d2ccc60fffd4f327"]},
|
||||
"hackney": {:hex, :hackney, "1.16.0", "5096ac8e823e3a441477b2d187e30dd3fff1a82991a806b2003845ce72ce2d84", [:rebar3], [{:certifi, "2.5.2", [hex: :certifi, repo: "hexpm", optional: false]}, {:idna, "6.0.1", [hex: :idna, repo: "hexpm", optional: false]}, {:metrics, "1.0.1", [hex: :metrics, repo: "hexpm", optional: false]}, {:mimerl, "~>1.1", [hex: :mimerl, repo: "hexpm", optional: false]}, {:parse_trans, "3.3.0", [hex: :parse_trans, repo: "hexpm", optional: false]}, {:ssl_verify_fun, "1.1.6", [hex: :ssl_verify_fun, repo: "hexpm", optional: false]}], "hexpm", "3bf0bebbd5d3092a3543b783bf065165fa5d3ad4b899b836810e513064134e18"},
|
||||
"hackney": {:hex, :hackney, "1.15.2", "07e33c794f8f8964ee86cebec1a8ed88db5070e52e904b8f12209773c1036085", [:rebar3], [{:certifi, "2.5.1", [hex: :certifi, repo: "hexpm", optional: false]}, {:idna, "6.0.0", [hex: :idna, repo: "hexpm", optional: false]}, {:metrics, "1.0.1", [hex: :metrics, repo: "hexpm", optional: false]}, {:mimerl, "~>1.1", [hex: :mimerl, repo: "hexpm", optional: false]}, {:ssl_verify_fun, "1.1.5", [hex: :ssl_verify_fun, repo: "hexpm", optional: false]}], "hexpm", "e0100f8ef7d1124222c11ad362c857d3df7cb5f4204054f9f0f4a728666591fc"},
|
||||
"html_entities": {:hex, :html_entities, "0.5.1", "1c9715058b42c35a2ab65edc5b36d0ea66dd083767bef6e3edb57870ef556549", [:mix], [], "hexpm", "30efab070904eb897ff05cd52fa61c1025d7f8ef3a9ca250bc4e6513d16c32de"},
|
||||
"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.0", "4e4b501a936dbf4cb5222597038a89ea10781776770d2e185849fa829686b34c", [:mix], [], "hexpm", "f8a7b3731e3fd17d38fa6e343fcad7b03d6874a3b0a108c8568a71ed9c2cf824"},
|
||||
"httpoison": {:hex, :httpoison, "1.7.0", "abba7d086233c2d8574726227b6c2c4f6e53c4deae7fe5f6de531162ce9929a0", [:mix], [{:hackney, "~> 1.16", [hex: :hackney, repo: "hexpm", optional: false]}], "hexpm", "975cc87c845a103d3d1ea1ccfd68a2700c211a434d8428b10c323dc95dc5b980"},
|
||||
"idna": {:hex, :idna, "6.0.1", "1d038fb2e7668ce41fbf681d2c45902e52b3cb9e9c77b55334353b222c2ee50c", [:rebar3], [{:unicode_util_compat, "0.5.0", [hex: :unicode_util_compat, repo: "hexpm", optional: false]}], "hexpm", "a02c8a1c4fd601215bb0b0324c8a6986749f807ce35f25449ec9e69758708122"},
|
||||
"httpoison": {:hex, :httpoison, "1.6.2", "ace7c8d3a361cebccbed19c283c349b3d26991eff73a1eaaa8abae2e3c8089b6", [:mix], [{:hackney, "~> 1.15 and >= 1.15.2", [hex: :hackney, repo: "hexpm", optional: false]}], "hexpm", "aa2c74bd271af34239a3948779612f87df2422c2fdcfdbcec28d9c105f0773fe"},
|
||||
"idna": {:hex, :idna, "6.0.0", "689c46cbcdf3524c44d5f3dde8001f364cd7608a99556d8fbd8239a5798d4c10", [:rebar3], [{:unicode_util_compat, "0.4.1", [hex: :unicode_util_compat, repo: "hexpm", optional: false]}], "hexpm", "4bdd305eb64e18b0273864920695cb18d7a2021f31a11b9c5fbcd9a253f936e2"},
|
||||
"inet_cidr": {:hex, :inet_cidr, "1.0.4", "a05744ab7c221ca8e395c926c3919a821eb512e8f36547c062f62c4ca0cf3d6e", [:mix], [], "hexpm", "64a2d30189704ae41ca7dbdd587f5291db5d1dda1414e0774c29ffc81088c1bc"},
|
||||
"jason": {:hex, :jason, "1.2.1", "12b22825e22f468c02eb3e4b9985f3d0cb8dc40b9bd704730efa11abd2708c44", [:mix], [{:decimal, "~> 1.0", [hex: :decimal, repo: "hexpm", optional: true]}], "hexpm", "b659b8571deedf60f79c5a608e15414085fa141344e2716fbd6988a084b5f993"},
|
||||
"joken": {:hex, :joken, "2.2.0", "2daa1b12be05184aff7b5ace1d43ca1f81345962285fff3f88db74927c954d3a", [:mix], [{:jose, "~> 1.9", [hex: :jose, repo: "hexpm", optional: false]}], "hexpm", "b4f92e30388206f869dd25d1af628a1d99d7586e5cf0672f64d4df84c4d2f5e9"},
|
||||
|
@ -105,17 +105,17 @@
|
|||
"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"]},
|
||||
"sleeplocks": {:hex, :sleeplocks, "1.1.1", "3d462a0639a6ef36cc75d6038b7393ae537ab394641beb59830a1b8271faeed3", [:rebar3], [], "hexpm", "84ee37aeff4d0d92b290fff986d6a95ac5eedf9b383fadfd1d88e9b84a1c02e1"},
|
||||
"ssl_verify_fun": {:hex, :ssl_verify_fun, "1.1.6", "cf344f5692c82d2cd7554f5ec8fd961548d4fd09e7d22f5b62482e5aeaebd4b0", [:make, :mix, :rebar3], [], "hexpm", "bdb0d2471f453c88ff3908e7686f86f9be327d065cc1ec16fa4540197ea04680"},
|
||||
"ssl_verify_fun": {:hex, :ssl_verify_fun, "1.1.5", "6eaf7ad16cb568bb01753dbbd7a95ff8b91c7979482b95f38443fe2c8852a79b", [:make, :mix, :rebar3], [], "hexpm", "13104d7897e38ed7f044c4de953a6c28597d1c952075eb2e328bc6d6f2bfc496"},
|
||||
"sweet_xml": {:hex, :sweet_xml, "0.6.6", "fc3e91ec5dd7c787b6195757fbcf0abc670cee1e4172687b45183032221b66b8", [:mix], [], "hexpm", "2e1ec458f892ffa81f9f8386e3f35a1af6db7a7a37748a64478f13163a1f3573"},
|
||||
"swoosh": {:hex, :swoosh, "1.0.0", "c547cfc83f30e12d5d1fdcb623d7de2c2e29a5becfc68bf8f42ba4d23d2c2756", [:mix], [{:cowboy, "~> 1.0.1 or ~> 1.1 or ~> 2.4", [hex: :cowboy, repo: "hexpm", optional: true]}, {:gen_smtp, "~> 0.13", [hex: :gen_smtp, repo: "hexpm", optional: true]}, {:hackney, "~> 1.9", [hex: :hackney, repo: "hexpm", optional: true]}, {:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: false]}, {:mail, "~> 0.2", [hex: :mail, repo: "hexpm", optional: true]}, {:mime, "~> 1.1", [hex: :mime, repo: "hexpm", optional: false]}, {:plug_cowboy, ">= 1.0.0", [hex: :plug_cowboy, repo: "hexpm", optional: true]}], "hexpm", "b3b08e463f876cb6167f7168e9ad99a069a724e124bcee61847e0e1ed13f4a0d"},
|
||||
"syslog": {:hex, :syslog, "1.1.0", "6419a232bea84f07b56dc575225007ffe34d9fdc91abe6f1b2f254fd71d8efc2", [:rebar3], [], "hexpm", "4c6a41373c7e20587be33ef841d3de6f3beba08519809329ecc4d27b15b659e1"},
|
||||
"telemetry": {:hex, :telemetry, "0.4.2", "2808c992455e08d6177322f14d3bdb6b625fbcfd233a73505870d8738a2f4599", [:rebar3], [], "hexpm", "2d1419bd9dda6a206d7b5852179511722e2b18812310d304620c7bd92a13fcef"},
|
||||
"tesla": {:git, "https://git.pleroma.social/pleroma/elixir-libraries/tesla.git", "3a2789d8535f7b520ebbadc4494227e5ba0e5365", [ref: "3a2789d8535f7b520ebbadc4494227e5ba0e5365"]},
|
||||
"tesla": {:git, "https://github.com/teamon/tesla/", "9f7261ca49f9f901ceb73b60219ad6f8a9f6aa30", [ref: "9f7261ca49f9f901ceb73b60219ad6f8a9f6aa30"]},
|
||||
"timex": {:hex, :timex, "3.6.2", "845cdeb6119e2fef10751c0b247b6c59d86d78554c83f78db612e3290f819bc2", [:mix], [{:combine, "~> 0.10", [hex: :combine, repo: "hexpm", optional: false]}, {:gettext, "~> 0.10", [hex: :gettext, repo: "hexpm", optional: false]}, {:tzdata, "~> 0.1.8 or ~> 0.5 or ~> 1.0.0", [hex: :tzdata, repo: "hexpm", optional: false]}], "hexpm", "26030b46199d02a590be61c2394b37ea25a3664c02fafbeca0b24c972025d47a"},
|
||||
"trailing_format_plug": {:hex, :trailing_format_plug, "0.0.7", "64b877f912cf7273bed03379936df39894149e35137ac9509117e59866e10e45", [:mix], [{:plug, "> 0.12.0", [hex: :plug, repo: "hexpm", optional: false]}], "hexpm", "bd4fde4c15f3e993a999e019d64347489b91b7a9096af68b2bdadd192afa693f"},
|
||||
"tzdata": {:hex, :tzdata, "1.0.3", "73470ad29dde46e350c60a66e6b360d3b99d2d18b74c4c349dbebbc27a09a3eb", [:mix], [{:hackney, "~> 1.0", [hex: :hackney, repo: "hexpm", optional: false]}], "hexpm", "a6e1ee7003c4d04ecbd21dd3ec690d4c6662db5d3bbdd7262d53cdf5e7c746c1"},
|
||||
"ueberauth": {:hex, :ueberauth, "0.6.3", "d42ace28b870e8072cf30e32e385579c57b9cc96ec74fa1f30f30da9c14f3cc0", [:mix], [{:plug, "~> 1.5", [hex: :plug, repo: "hexpm", optional: false]}], "hexpm", "afc293d8a1140d6591b53e3eaf415ca92842cb1d32fad3c450c6f045f7f91b60"},
|
||||
"unicode_util_compat": {:hex, :unicode_util_compat, "0.5.0", "8516502659002cec19e244ebd90d312183064be95025a319a6c7e89f4bccd65b", [:rebar3], [], "hexpm", "d48d002e15f5cc105a696cf2f1bbb3fc72b4b770a184d8420c8db20da2674b38"},
|
||||
"unicode_util_compat": {:hex, :unicode_util_compat, "0.4.1", "d869e4c68901dd9531385bb0c8c40444ebf624e60b6962d95952775cac5e90cd", [:rebar3], [], "hexpm", "1d1848c40487cdb0b30e8ed975e34e025860c02e419cb615d255849f3427439d"},
|
||||
"unsafe": {:hex, :unsafe, "1.0.1", "a27e1874f72ee49312e0a9ec2e0b27924214a05e3ddac90e91727bc76f8613d8", [:mix], [], "hexpm", "6c7729a2d214806450d29766abc2afaa7a2cbecf415be64f36a6691afebb50e5"},
|
||||
"web_push_encryption": {:hex, :web_push_encryption, "0.3.0", "598b5135e696fd1404dc8d0d7c0fa2c027244a4e5d5e5a98ba267f14fdeaabc8", [:mix], [{:httpoison, "~> 1.0", [hex: :httpoison, repo: "hexpm", optional: false]}, {:jose, "~> 1.8", [hex: :jose, repo: "hexpm", optional: false]}], "hexpm", "f10bdd1afe527ede694749fb77a2f22f146a51b054c7fa541c9fd920fba7c875"},
|
||||
"websocket_client": {:git, "https://github.com/jeremyong/websocket_client.git", "9a6f65d05ebf2725d62fb19262b21f1805a59fbf", []},
|
||||
|
|
|
@ -0,0 +1,13 @@
|
|||
defmodule Pleroma.Repo.Migrations.RenameAwaitUpTimeoutInConnectionsPool do
|
||||
use Ecto.Migration
|
||||
|
||||
def change do
|
||||
with %Pleroma.ConfigDB{} = config <-
|
||||
Pleroma.ConfigDB.get_by_params(%{group: :pleroma, key: :connections_pool}),
|
||||
{timeout, value} when is_integer(timeout) <- Keyword.pop(config.value, :await_up_timeout) do
|
||||
config
|
||||
|> Ecto.Changeset.change(value: Keyword.put(value, :connect_timeout, timeout))
|
||||
|> Pleroma.Repo.update()
|
||||
end
|
||||
end
|
||||
end
|
|
@ -0,0 +1,19 @@
|
|||
defmodule Pleroma.Repo.Migrations.RenameTimeoutInPools do
|
||||
use Ecto.Migration
|
||||
|
||||
def change do
|
||||
with %Pleroma.ConfigDB{} = config <-
|
||||
Pleroma.ConfigDB.get_by_params(%{group: :pleroma, key: :pools}) do
|
||||
updated_value =
|
||||
Enum.map(config.value, fn {pool, pool_value} ->
|
||||
with {timeout, value} when is_integer(timeout) <- Keyword.pop(pool_value, :timeout) do
|
||||
{pool, Keyword.put(value, :recv_timeout, timeout)}
|
||||
end
|
||||
end)
|
||||
|
||||
config
|
||||
|> Ecto.Changeset.change(value: updated_value)
|
||||
|> Pleroma.Repo.update()
|
||||
end
|
||||
end
|
||||
end
|
|
@ -0,0 +1,19 @@
|
|||
defmodule Pleroma.Repo.Migrations.RemoveCronStatsWorkerFromObanConfig do
|
||||
use Ecto.Migration
|
||||
|
||||
def change do
|
||||
with %Pleroma.ConfigDB{} = config <-
|
||||
Pleroma.ConfigDB.get_by_params(%{group: :pleroma, key: Oban}),
|
||||
crontab when is_list(crontab) <- config.value[:crontab],
|
||||
index when is_integer(index) <-
|
||||
Enum.find_index(crontab, fn {_, worker} ->
|
||||
worker == Pleroma.Workers.Cron.StatsWorker
|
||||
end) do
|
||||
updated_value = Keyword.put(config.value, :crontab, List.delete_at(crontab, index))
|
||||
|
||||
config
|
||||
|> Ecto.Changeset.change(value: updated_value)
|
||||
|> Pleroma.Repo.update()
|
||||
end
|
||||
end
|
||||
end
|
|
@ -1 +1 @@
|
|||
<!DOCTYPE html><html lang=en><head><meta charset=utf-8><meta name=viewport content="width=device-width,initial-scale=1,user-scalable=no"><title>Pleroma</title><!--server-generated-meta--><link rel=icon type=image/png href=/favicon.png><link href=/static/css/app.77b1644622e3bae24b6b.css rel=stylesheet><link href=/static/fontello.1598361006087.css rel=stylesheet></head><body class=hidden><noscript>To use Pleroma, please enable JavaScript.</noscript><div id=app></div><script type=text/javascript src=/static/js/vendors~app.bc5812c087f5dbcb914d.js></script><script type=text/javascript src=/static/js/app.154c25316542278028a6.js></script></body></html>
|
||||
<!DOCTYPE html><html lang=en><head><meta charset=utf-8><meta name=viewport content="width=device-width,initial-scale=1,user-scalable=no"><title>Pleroma</title><!--server-generated-meta--><link rel=icon type=image/png href=/favicon.png><link href=/static/css/app.77b1644622e3bae24b6b.css rel=stylesheet><link href=/static/fontello.1599568314856.css rel=stylesheet></head><body class=hidden><noscript>To use Pleroma, please enable JavaScript.</noscript><div id=app></div><script type=text/javascript src=/static/js/vendors~app.90c4af83c1ae68f4cd95.js></script><script type=text/javascript src=/static/js/app.55d173dc5e39519aa518.js></script></body></html>
|
Binary file not shown.
Binary file not shown.
Before Width: | Height: | Size: 28 KiB After Width: | Height: | Size: 28 KiB |
Binary file not shown.
Binary file not shown.
BIN
priv/static/static/font/fontello.1599568314856.woff2
Normal file
BIN
priv/static/static/font/fontello.1599568314856.woff2
Normal file
Binary file not shown.
|
@ -1,11 +1,11 @@
|
|||
@font-face {
|
||||
font-family: "Icons";
|
||||
src: url("./font/fontello.1598361006087.eot");
|
||||
src: url("./font/fontello.1598361006087.eot") format("embedded-opentype"),
|
||||
url("./font/fontello.1598361006087.woff2") format("woff2"),
|
||||
url("./font/fontello.1598361006087.woff") format("woff"),
|
||||
url("./font/fontello.1598361006087.ttf") format("truetype"),
|
||||
url("./font/fontello.1598361006087.svg") format("svg");
|
||||
src: url("./font/fontello.1599568314856.eot");
|
||||
src: url("./font/fontello.1599568314856.eot") format("embedded-opentype"),
|
||||
url("./font/fontello.1599568314856.woff2") format("woff2"),
|
||||
url("./font/fontello.1599568314856.woff") format("woff"),
|
||||
url("./font/fontello.1599568314856.ttf") format("truetype"),
|
||||
url("./font/fontello.1599568314856.svg") format("svg");
|
||||
font-weight: normal;
|
||||
font-style: normal;
|
||||
}
|
File diff suppressed because one or more lines are too long
2
priv/static/static/js/10.46fbbdfaf0d4800f349b.js
Normal file
2
priv/static/static/js/10.46fbbdfaf0d4800f349b.js
Normal file
File diff suppressed because one or more lines are too long
|
@ -1 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/10.1c5cd5fbe554eca63dfe.js","sourceRoot":""}
|
||||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/10.46fbbdfaf0d4800f349b.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
2
priv/static/static/js/12.b3bf0bc313861d6ec36b.js
Normal file
2
priv/static/static/js/12.b3bf0bc313861d6ec36b.js
Normal file
File diff suppressed because one or more lines are too long
|
@ -1 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/12.6619e0b2f854637e76d4.js","sourceRoot":""}
|
||||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/12.b3bf0bc313861d6ec36b.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
|
@ -1 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/13.c843797f3e374f0e3e1a.js","sourceRoot":""}
|
||||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/13.adb8a942514d735722c4.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
|
@ -1 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/14.71f8caca49093a99e871.js","sourceRoot":""}
|
||||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/14.d015d9b2ea16407e389c.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
1
priv/static/static/js/18.94946caca48930c224c7.js.map
Normal file
1
priv/static/static/js/18.94946caca48930c224c7.js.map
Normal file
|
@ -0,0 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/18.94946caca48930c224c7.js","sourceRoot":""}
|
|
@ -1 +0,0 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/18.b29eedabe76445fe94b8.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
1
priv/static/static/js/19.233c81ac2c28d55e9f13.js.map
Normal file
1
priv/static/static/js/19.233c81ac2c28d55e9f13.js.map
Normal file
|
@ -0,0 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/19.233c81ac2c28d55e9f13.js","sourceRoot":""}
|
|
@ -1 +0,0 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/19.ed1cd5db596618779f03.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
1
priv/static/static/js/2.c92f4803ff24726cea58.js.map
Normal file
1
priv/static/static/js/2.c92f4803ff24726cea58.js.map
Normal file
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
@ -1 +0,0 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/20.6d311b830d8ac672729f.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
1
priv/static/static/js/20.818c38d27369c3a4d677.js.map
Normal file
1
priv/static/static/js/20.818c38d27369c3a4d677.js.map
Normal file
|
@ -0,0 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/20.818c38d27369c3a4d677.js","sourceRoot":""}
|
|
@ -1 +0,0 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/23.2c5f0fd2f2acd04592e8.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
1
priv/static/static/js/23.a57a7845cc20fafd06d1.js.map
Normal file
1
priv/static/static/js/23.a57a7845cc20fafd06d1.js.map
Normal file
|
@ -0,0 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/23.a57a7845cc20fafd06d1.js","sourceRoot":""}
|
|
@ -1 +0,0 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/25.365514e44606a895ab50.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
1
priv/static/static/js/25.5a9efe20e3ae1352e6d2.js.map
Normal file
1
priv/static/static/js/25.5a9efe20e3ae1352e6d2.js.map
Normal file
|
@ -0,0 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/25.5a9efe20e3ae1352e6d2.js","sourceRoot":""}
|
|
@ -1 +0,0 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/28.9eb3e783aeba24c84f0a.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
1
priv/static/static/js/28.e0f9f164e0bfd890dc61.js.map
Normal file
1
priv/static/static/js/28.e0f9f164e0bfd890dc61.js.map
Normal file
|
@ -0,0 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/28.e0f9f164e0bfd890dc61.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
@ -1 +0,0 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/30.a9377272337674f2dd05.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
1
priv/static/static/js/30.fce58be0b52ca3e32fa4.js.map
Normal file
1
priv/static/static/js/30.fce58be0b52ca3e32fa4.js.map
Normal file
|
@ -0,0 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/30.fce58be0b52ca3e32fa4.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
|
@ -1 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/8.5f48d6f0cbed548baf0f.js","sourceRoot":""}
|
||||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/8.636322a87bb10a1754f8.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
|
@ -1 +1 @@
|
|||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/9.a95fcd286ba2c9050c4d.js","sourceRoot":""}
|
||||
{"version":3,"sources":[],"names":[],"mappings":"","file":"static/js/9.6010dbcce7b4d7c05a18.js","sourceRoot":""}
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
2
priv/static/static/js/app.55d173dc5e39519aa518.js
Normal file
2
priv/static/static/js/app.55d173dc5e39519aa518.js
Normal file
File diff suppressed because one or more lines are too long
1
priv/static/static/js/app.55d173dc5e39519aa518.js.map
Normal file
1
priv/static/static/js/app.55d173dc5e39519aa518.js.map
Normal file
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue