diff --git a/installation/akkoma.service b/installation/akkoma.service index 717693495..4945e108c 100644 --- a/installation/akkoma.service +++ b/installation/akkoma.service @@ -19,6 +19,9 @@ Environment="MIX_ENV=prod" ; Don't listen epmd on 0.0.0.0 Environment="ERL_EPMD_ADDRESS=127.0.0.1" +; Don't busy wait +Environment="ERL_AFLAGS=+sbwt none +sbwtdcpu none +sbwtdio none" + ; Make sure that all paths fit your installation. ; Path to the home directory of the user running the Akkoma service. Environment="HOME=/var/lib/akkoma" diff --git a/installation/init.d/akkoma b/installation/init.d/akkoma index bd17516f2..a03b494c0 100755 --- a/installation/init.d/akkoma +++ b/installation/init.d/akkoma @@ -1,23 +1,43 @@ #!/sbin/openrc-run supervisor=supervise-daemon -command_user=akkoma:akkoma -command_background=1 -# Ask process to terminate within 30 seconds, otherwise kill it -retry="SIGTERM/30/SIGKILL/5" -pidfile="/var/run/akkoma.pid" -directory=/opt/akkoma -healthcheck_delay=60 -healthcheck_timer=30 no_new_privs="yes" +pidfile="/var/run/akkoma.pid" -: ${akkoma_port:-4000} +# Ask process first to terminate itself within 60s, otherwise kill it +retry="SIGTERM/60/SIGKILL/5" -# Needs OpenRC >= 0.42 -#respawn_max=0 -#respawn_delay=5 +# if you really want to use start-stop-daemon instead, +# also put the following in the config: +# command_background=1 + +# Adjust defaults as needed in /etc/conf.d/akkoma; +# no need to directly edit the service file +command_user="${command_user:-akkoma:akkoma}" +directory="${directory:-/var/lib/akkoma/akkoma}" +akkoma_port="${akkoma_port:-4000}" +# whether to allow connecting a remote exlixir shell to the running Akkoma instance +akkoma_console=${akkoma_console:-NO} + +output_log="${output_log:-/var/log/akkoma}" +error_log="${error_log:-/var/log/akkoma}" + +# 0 means unlimited restarts +respawn_max="${respawn_max:-0}" +respawn_delay="${respawn_delay:-5}" +# define respawn period to only count crashes within a +# sliding time window towards respawn_max, e.g.: +# respawn_period=2850 + +healthcheck_delay="${healthcheck_delay:-60}" +healthcheck_timer="${healthcheck_timer:-30}" + +MIX_ENV=prod +ERL_EPMD_ADDRESS="${ERL_EPMD_ADDRESS:-127.0.0.1}" +ERL_AFLAGS="${ERL_AFLAGS:-+sbwt none +sbwtdcpu none +sbwtdio none}" +supervise_daemon_args="${supervise_daemon_args} --env MIX_ENV=${MIX_ENV}" +supervise_daemon_args="${supervise_daemon_args} --env ERL_EPMD_ADDRESS=${ERL_EPMD_ADDRESS}" +supervise_daemon_args="${supervise_daemon_args} --env ERL_AFLAGS='${ERL_AFLAGS}'" -# put akkoma_console=YES in /etc/conf.d/akkoma if you want to be able to -# connect to akkoma via an elixir console if yesno "${akkoma_console}"; then command=elixir command_args="--name akkoma@127.0.0.1 --erl '-kernel inet_dist_listen_min 9001 inet_dist_listen_max 9001 inet_dist_use_interface {127,0,0,1}' -S mix phx.server" @@ -31,13 +51,24 @@ else command_args="phx.server" fi -export MIX_ENV=prod -export ERL_EPMD_ADDRESS=127.0.0.1 - depend() { need nginx postgresql } +start_pre() { + # Ensure logfile ownership and perms are alright + checkpath --file --owner "$command_user" "$output_log" "$error_log" \ + || eerror "Logfile(s) not owned by $command_user, or not a file!" + checkpath --writable "$output_log" "$error_log" \ + || eerror "Logfile(s) not writable!" + + # If a recompile is needed perform it with lowest prio + # (delaying the actual start) to avoid hogging too much + # CPU from other services + cd "$directory" + doas -u "${command_user%%:*}" env MIX_ENV="$MIX_ENV" nice -n 19 "$command" compile +} + healthcheck() { # put akkoma_health=YES in /etc/conf.d/akkoma if you want healthchecking # and make sure you have curl installed diff --git a/lib/pleroma/user.ex b/lib/pleroma/user.ex index 14414adc4..2bc3e9ace 100644 --- a/lib/pleroma/user.ex +++ b/lib/pleroma/user.ex @@ -1624,8 +1624,12 @@ def blocks_user?(%User{} = user, %User{} = target) do def blocks_user?(_, _), do: false - def blocks_domain?(%User{} = user, %User{} = target) do - %{host: host} = URI.parse(target.ap_id) + def blocks_domain?(%User{} = user, %User{ap_id: ap_id}) do + blocks_domain?(user, ap_id) + end + + def blocks_domain?(%User{} = user, url) when is_binary(url) do + %{host: host} = URI.parse(url) Enum.member?(user.domain_blocks, host) # TODO: functionality should probably be changed such that subdomains block as well, # but as it stands, this just hecks up the relationships endpoint diff --git a/lib/pleroma/web/pleroma_api/controllers/emoji_reaction_controller.ex b/lib/pleroma/web/pleroma_api/controllers/emoji_reaction_controller.ex index e762fcad8..66cff7aaa 100644 --- a/lib/pleroma/web/pleroma_api/controllers/emoji_reaction_controller.ex +++ b/lib/pleroma/web/pleroma_api/controllers/emoji_reaction_controller.ex @@ -52,6 +52,14 @@ defp filter_allowed_user_by_ap_id(ap_ids, excluded_ap_ids) do end) end + defp filter_allowed_users_by_domain(ap_ids, %User{} = for_user) do + Enum.reject(ap_ids, fn ap_id -> + User.blocks_domain?(for_user, ap_id) + end) + end + + defp filter_allowed_users_by_domain(ap_ids, nil), do: ap_ids + def filter_allowed_users(reactions, user, with_muted) do exclude_ap_ids = if is_nil(user) do @@ -62,7 +70,10 @@ def filter_allowed_users(reactions, user, with_muted) do end filter_emoji = fn emoji, users, url -> - case filter_allowed_user_by_ap_id(users, exclude_ap_ids) do + users + |> filter_allowed_user_by_ap_id(exclude_ap_ids) + |> filter_allowed_users_by_domain(user) + |> case do [] -> nil users -> {emoji, users, url} end diff --git a/mix.lock b/mix.lock index fbecdc528..09997f29d 100644 --- a/mix.lock +++ b/mix.lock @@ -18,7 +18,7 @@ "cowboy": {:hex, :cowboy, "2.12.0", "f276d521a1ff88b2b9b4c54d0e753da6c66dd7be6c9fca3d9418b561828a3731", [:make, :rebar3], [{:cowlib, "2.13.0", [hex: :cowlib, repo: "hexpm", optional: false]}, {:ranch, "1.8.0", [hex: :ranch, repo: "hexpm", optional: false]}], "hexpm", "8a7abe6d183372ceb21caa2709bec928ab2b72e18a3911aa1771639bef82651e"}, "cowboy_telemetry": {:hex, :cowboy_telemetry, "0.4.0", "f239f68b588efa7707abce16a84d0d2acf3a0f50571f8bb7f56a15865aae820c", [:rebar3], [{:cowboy, "~> 2.7", [hex: :cowboy, repo: "hexpm", optional: false]}, {:telemetry, "~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "7d98bac1ee4565d31b62d59f8823dfd8356a169e7fcbb83831b8a5397404c9de"}, "cowlib": {:hex, :cowlib, "2.13.0", "db8f7505d8332d98ef50a3ef34b34c1afddec7506e4ee4dd4a3a266285d282ca", [:make, :rebar3], [], "hexpm", "e1e1284dc3fc030a64b1ad0d8382ae7e99da46c3246b815318a4b848873800a4"}, - "credo": {:hex, :credo, "1.7.6", "b8f14011a5443f2839b04def0b252300842ce7388f3af177157c86da18dfbeea", [:mix], [{:bunt, "~> 0.2.1 or ~> 1.0", [hex: :bunt, repo: "hexpm", optional: false]}, {:file_system, "~> 0.2 or ~> 1.0", [hex: :file_system, repo: "hexpm", optional: false]}, {:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: false]}], "hexpm", "146f347fb9f8cbc5f7e39e3f22f70acbef51d441baa6d10169dd604bfbc55296"}, + "credo": {:hex, :credo, "1.7.7", "771445037228f763f9b2afd612b6aa2fd8e28432a95dbbc60d8e03ce71ba4446", [:mix], [{:bunt, "~> 0.2.1 or ~> 1.0", [hex: :bunt, repo: "hexpm", optional: false]}, {:file_system, "~> 0.2 or ~> 1.0", [hex: :file_system, repo: "hexpm", optional: false]}, {:jason, "~> 1.0", [hex: :jason, repo: "hexpm", optional: false]}], "hexpm", "8bc87496c9aaacdc3f90f01b7b0582467b69b4bd2441fe8aae3109d843cc2f2e"}, "custom_base": {:hex, :custom_base, "0.2.1", "4a832a42ea0552299d81652aa0b1f775d462175293e99dfbe4d7dbaab785a706", [:mix], [], "hexpm", "8df019facc5ec9603e94f7270f1ac73ddf339f56ade76a721eaa57c1493ba463"}, "db_connection": {:hex, :db_connection, "2.6.0", "77d835c472b5b67fc4f29556dee74bf511bbafecdcaf98c27d27fa5918152086", [:mix], [{:telemetry, "~> 0.4 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "c2f992d15725e721ec7fbc1189d4ecdb8afef76648c746a8e1cad35e3b8a35f3"}, "decimal": {:hex, :decimal, "2.1.1", "5611dca5d4b2c3dd497dec8f68751f1f1a54755e8ed2a966c2633cf885973ad6", [:mix], [], "hexpm", "53cfe5f497ed0e7771ae1a475575603d77425099ba5faef9394932b35020ffcc"}, @@ -94,7 +94,7 @@ "phoenix_pubsub": {:hex, :phoenix_pubsub, "2.1.3", "3168d78ba41835aecad272d5e8cd51aa87a7ac9eb836eabc42f6e57538e3731d", [:mix], [], "hexpm", "bba06bc1dcfd8cb086759f0edc94a8ba2bc8896d5331a1e2c2902bf8e36ee502"}, "phoenix_swoosh": {:hex, :phoenix_swoosh, "1.2.1", "b74ccaa8046fbc388a62134360ee7d9742d5a8ae74063f34eb050279de7a99e1", [:mix], [{:finch, "~> 0.8", [hex: :finch, repo: "hexpm", optional: true]}, {:hackney, "~> 1.10", [hex: :hackney, repo: "hexpm", optional: true]}, {:phoenix, "~> 1.6", [hex: :phoenix, repo: "hexpm", optional: true]}, {:phoenix_html, "~> 3.0 or ~> 4.0", [hex: :phoenix_html, repo: "hexpm", optional: true]}, {:phoenix_view, "~> 1.0 or ~> 2.0", [hex: :phoenix_view, repo: "hexpm", optional: false]}, {:swoosh, "~> 1.5", [hex: :swoosh, repo: "hexpm", optional: false]}], "hexpm", "4000eeba3f9d7d1a6bf56d2bd56733d5cadf41a7f0d8ffe5bb67e7d667e204a2"}, "phoenix_template": {:hex, :phoenix_template, "1.0.4", "e2092c132f3b5e5b2d49c96695342eb36d0ed514c5b252a77048d5969330d639", [:mix], [{:phoenix_html, "~> 2.14.2 or ~> 3.0 or ~> 4.0", [hex: :phoenix_html, repo: "hexpm", optional: true]}], "hexpm", "2c0c81f0e5c6753faf5cca2f229c9709919aba34fab866d3bc05060c9c444206"}, - "phoenix_view": {:hex, :phoenix_view, "2.0.3", "4d32c4817fce933693741deeb99ef1392619f942633dde834a5163124813aad3", [:mix], [{:phoenix_html, "~> 2.14.2 or ~> 3.0 or ~> 4.0", [hex: :phoenix_html, repo: "hexpm", optional: true]}, {:phoenix_template, "~> 1.0", [hex: :phoenix_template, repo: "hexpm", optional: false]}], "hexpm", "cd34049af41be2c627df99cd4eaa71fc52a328c0c3d8e7d4aa28f880c30e7f64"}, + "phoenix_view": {:hex, :phoenix_view, "2.0.4", "b45c9d9cf15b3a1af5fb555c674b525391b6a1fe975f040fb4d913397b31abf4", [:mix], [{:phoenix_html, "~> 2.14.2 or ~> 3.0 or ~> 4.0", [hex: :phoenix_html, repo: "hexpm", optional: true]}, {:phoenix_template, "~> 1.0", [hex: :phoenix_template, repo: "hexpm", optional: false]}], "hexpm", "4e992022ce14f31fe57335db27a28154afcc94e9983266835bb3040243eb620b"}, "plug": {:hex, :plug, "1.16.0", "1d07d50cb9bb05097fdf187b31cf087c7297aafc3fed8299aac79c128a707e47", [:mix], [{:mime, "~> 1.0 or ~> 2.0", [hex: :mime, repo: "hexpm", optional: false]}, {:plug_crypto, "~> 1.1.1 or ~> 1.2 or ~> 2.0", [hex: :plug_crypto, repo: "hexpm", optional: false]}, {:telemetry, "~> 0.4.3 or ~> 1.0", [hex: :telemetry, repo: "hexpm", optional: false]}], "hexpm", "cbf53aa1f5c4d758a7559c0bd6d59e286c2be0c6a1fac8cc3eee2f638243b93e"}, "plug_cowboy": {:hex, :plug_cowboy, "2.7.1", "87677ffe3b765bc96a89be7960f81703223fe2e21efa42c125fcd0127dd9d6b2", [:mix], [{:cowboy, "~> 2.7", [hex: :cowboy, repo: "hexpm", optional: false]}, {:cowboy_telemetry, "~> 0.3", [hex: :cowboy_telemetry, repo: "hexpm", optional: false]}, {:plug, "~> 1.14", [hex: :plug, repo: "hexpm", optional: false]}], "hexpm", "02dbd5f9ab571b864ae39418db7811618506256f6d13b4a45037e5fe78dc5de3"}, "plug_crypto": {:hex, :plug_crypto, "2.1.0", "f44309c2b06d249c27c8d3f65cfe08158ade08418cf540fd4f72d4d6863abb7b", [:mix], [], "hexpm", "131216a4b030b8f8ce0f26038bc4421ae60e4bb95c5cf5395e1421437824c4fa"}, diff --git a/test/pleroma/user_test.exs b/test/pleroma/user_test.exs index de71f4b95..e3f0bb415 100644 --- a/test/pleroma/user_test.exs +++ b/test/pleroma/user_test.exs @@ -1149,6 +1149,18 @@ test "it blocks people" do assert User.blocks?(user, blocked_user) end + test "it blocks domains" do + user = insert(:user) + blocked_user = insert(:user) + + refute User.blocks_domain?(user, blocked_user) + + url = URI.parse(blocked_user.ap_id) + {:ok, user} = User.block_domain(user, url.host) + + assert User.blocks_domain?(user, blocked_user) + end + test "it unblocks users" do user = insert(:user) blocked_user = insert(:user) @@ -1159,6 +1171,17 @@ test "it unblocks users" do refute User.blocks?(user, blocked_user) end + test "it unblocks domains" do + user = insert(:user) + blocked_user = insert(:user) + + url = URI.parse(blocked_user.ap_id) + {:ok, user} = User.block_domain(user, url.host) + {:ok, user} = User.unblock_domain(user, url.host) + + refute User.blocks_domain?(user, blocked_user) + end + test "blocks tear down cyclical follow relationships" do blocker = insert(:user) blocked = insert(:user) diff --git a/test/pleroma/web/mastodon_api/views/status_view_test.exs b/test/pleroma/web/mastodon_api/views/status_view_test.exs index 7db3e3e61..6421df132 100644 --- a/test/pleroma/web/mastodon_api/views/status_view_test.exs +++ b/test/pleroma/web/mastodon_api/views/status_view_test.exs @@ -33,6 +33,10 @@ test "has an emoji reaction list" do user = insert(:user) other_user = insert(:user) third_user = insert(:user) + domain_blocked_user = insert(:user, %{ap_id: "https://blocked.com/@blocked"}) + + {:ok, user} = User.block_domain(user, "blocked.com") + {:ok, activity} = CommonAPI.post(user, %{status: "dae cofe??"}) {:ok, _} = CommonAPI.react_with_emoji(activity.id, user, "☕") @@ -40,6 +44,8 @@ test "has an emoji reaction list" do {:ok, _} = CommonAPI.react_with_emoji(activity.id, third_user, "🍵") {:ok, _} = CommonAPI.react_with_emoji(activity.id, other_user, "☕") {:ok, _} = CommonAPI.react_with_emoji(activity.id, other_user, ":dinosaur:") + # this should not show up when the user is viewing the status + {:ok, _} = CommonAPI.react_with_emoji(activity.id, domain_blocked_user, "😈") activity = Repo.get(Activity, activity.id) status = StatusView.render("show.json", activity: activity) @@ -55,7 +61,8 @@ test "has an emoji reaction list" do url: "http://localhost:4001/emoji/dino walking.gif", account_ids: [other_user.id, user.id] }, - %{name: "🍵", count: 1, me: false, url: nil, account_ids: [third_user.id]} + %{name: "🍵", count: 1, me: false, url: nil, account_ids: [third_user.id]}, + %{name: "😈", count: 1, me: false, url: nil, account_ids: [domain_blocked_user.id]} ] status = StatusView.render("show.json", activity: activity, for: user) @@ -73,6 +80,8 @@ test "has an emoji reaction list" do }, %{name: "🍵", count: 1, me: false, url: nil, account_ids: [third_user.id]} ] + + refute Enum.any?(status[:pleroma][:emoji_reactions], fn reaction -> reaction[:name] == "😈" end) end test "works correctly with badly formatted emojis" do