Merge branch 'fix/rate-limiter-remoteip-behavior' into 'develop'

rate limiter: disable based on if remote ip was found, not on if the plug was enabled

Closes #1620

See merge request pleroma/pleroma!2296
This commit is contained in:
Haelwenn 2020-03-15 14:22:10 +00:00
commit 67a27825b1
5 changed files with 55 additions and 69 deletions

View file

@ -92,6 +92,8 @@ config :pleroma, :modules, runtime_dir: "test/fixtures/modules"
config :pleroma, Pleroma.Emails.NewUsersDigestEmail, enabled: true
config :pleroma, Pleroma.Plugs.RemoteIp, enabled: false
if File.exists?("./config/test.secret.exs") do
import_config "test.secret.exs"
else

View file

@ -78,7 +78,7 @@ defmodule Pleroma.Plugs.RateLimiter do
end
def call(conn, plug_opts) do
if disabled?() do
if disabled?(conn) do
handle_disabled(conn)
else
action_settings = action_settings(plug_opts)
@ -87,9 +87,9 @@ defmodule Pleroma.Plugs.RateLimiter do
end
defp handle_disabled(conn) do
if Config.get(:env) == :prod do
Logger.warn("Rate limiter is disabled for localhost/socket")
end
Logger.warn(
"Rate limiter disabled due to forwarded IP not being found. Please ensure your reverse proxy is providing the X-Forwarded-For header or disable the RemoteIP plug/rate limiter."
)
conn
end
@ -109,16 +109,21 @@ defmodule Pleroma.Plugs.RateLimiter do
end
end
def disabled? do
def disabled?(conn) do
localhost_or_socket =
Config.get([Pleroma.Web.Endpoint, :http, :ip])
|> Tuple.to_list()
|> Enum.join(".")
|> String.match?(~r/^local|^127.0.0.1/)
case Config.get([Pleroma.Web.Endpoint, :http, :ip]) do
{127, 0, 0, 1} -> true
{0, 0, 0, 0, 0, 0, 0, 1} -> true
{:local, _} -> true
_ -> false
end
remote_ip_disabled = not Config.get([Pleroma.Plugs.RemoteIp, :enabled])
remote_ip_not_found =
if Map.has_key?(conn.assigns, :remote_ip_found),
do: !conn.assigns.remote_ip_found,
else: false
localhost_or_socket and remote_ip_disabled
localhost_or_socket and remote_ip_not_found
end
@inspect_bucket_not_found {:error, :not_found}

View file

@ -7,6 +7,8 @@ defmodule Pleroma.Plugs.RemoteIp do
This is a shim to call [`RemoteIp`](https://git.pleroma.social/pleroma/remote_ip) but with runtime configuration.
"""
import Plug.Conn
@behaviour Plug
@headers ~w[
@ -26,11 +28,12 @@ defmodule Pleroma.Plugs.RemoteIp do
def init(_), do: nil
def call(conn, _) do
def call(%{remote_ip: original_remote_ip} = conn, _) do
config = Pleroma.Config.get(__MODULE__, [])
if Keyword.get(config, :enabled, false) do
RemoteIp.call(conn, remote_ip_opts(config))
%{remote_ip: new_remote_ip} = conn = RemoteIp.call(conn, remote_ip_opts(config))
assign(conn, :remote_ip_found, original_remote_ip != new_remote_ip)
else
conn
end

View file

@ -3,8 +3,7 @@
# SPDX-License-Identifier: AGPL-3.0-only
defmodule Pleroma.Plugs.RateLimiterTest do
use ExUnit.Case, async: true
use Plug.Test
use Pleroma.Web.ConnCase
alias Pleroma.Config
alias Pleroma.Plugs.RateLimiter
@ -36,29 +35,11 @@ defmodule Pleroma.Plugs.RateLimiterTest do
|> RateLimiter.init()
|> RateLimiter.action_settings()
end
end
test "it is disabled for localhost" do
Config.put([:rate_limit, @limiter_name], {1, 1})
test "it is disabled if it remote ip plug is enabled but no remote ip is found" do
Config.put([Pleroma.Web.Endpoint, :http, :ip], {127, 0, 0, 1})
Config.put([Pleroma.Plugs.RemoteIp, :enabled], false)
assert RateLimiter.disabled?() == true
end
test "it is disabled for socket" do
Config.put([:rate_limit, @limiter_name], {1, 1})
Config.put([Pleroma.Web.Endpoint, :http, :ip], {:local, "/path/to/pleroma.sock"})
Config.put([Pleroma.Plugs.RemoteIp, :enabled], false)
assert RateLimiter.disabled?() == true
end
test "it is enabled for socket when remote ip is enabled" do
Config.put([:rate_limit, @limiter_name], {1, 1})
Config.put([Pleroma.Web.Endpoint, :http, :ip], {:local, "/path/to/pleroma.sock"})
Config.put([Pleroma.Plugs.RemoteIp, :enabled], true)
assert RateLimiter.disabled?() == false
assert RateLimiter.disabled?(Plug.Conn.assign(build_conn(), :remote_ip_found, false))
end
test "it restricts based on config values" do
@ -93,7 +74,6 @@ defmodule Pleroma.Plugs.RateLimiterTest do
refute conn.resp_body
refute conn.halted
end
end
describe "options" do
test "`bucket_name` option overrides default bucket name" do

View file

@ -756,10 +756,6 @@ defmodule Pleroma.Web.MastodonAPI.AccountControllerTest do
end
describe "create account by app / rate limit" do
clear_config([Pleroma.Plugs.RemoteIp, :enabled]) do
Pleroma.Config.put([Pleroma.Plugs.RemoteIp, :enabled], true)
end
clear_config([:rate_limit, :app_account_creation]) do
Pleroma.Config.put([:rate_limit, :app_account_creation], {10_000, 2})
end