logo

pleroma

My custom branche(s) on git.pleroma.social/pleroma/pleroma git clone https://hacktivis.me/git/pleroma.git
commit: 5b19543f0afaaad7f8fc302946547ae5c18e8bb3
parent 7466136ad3288cc2b442495d40af6e0787b250fb
Author: Ilja <ilja@ilja.space>
Date:   Sat, 21 May 2022 18:48:21 +0200

Add new setting and Plug to allow for privilege settings for staff

Diffstat:

Mconfig/config.exs2++
Mconfig/description.exs12++++++++++++
Alib/pleroma/web/plugs/ensure_privileged_plug.ex44++++++++++++++++++++++++++++++++++++++++++++
Atest/pleroma/web/plugs/ensure_privileged_plug_test.exs96+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
4 files changed, 154 insertions(+), 0 deletions(-)

diff --git a/config/config.exs b/config/config.exs @@ -257,6 +257,8 @@ config :pleroma, :instance, password_reset_token_validity: 60 * 60 * 24, profile_directory: true, privileged_staff: false, + admin_privileges: [], + moderator_privileges: [], max_endorsed_users: 20, birthday_required: false, birthday_min_age: 0, diff --git a/config/description.exs b/config/description.exs @@ -967,6 +967,18 @@ config :pleroma, :config_description, [ "Let moderators access sensitive data (e.g. updating user credentials, get password reset token, delete users, index and read private statuses and chats)" }, %{ + key: :admin_privileges, + type: {:list, :atom}, + suggestions: [], + description: "What extra priviledges to allow admins (e.g. updating user credentials, get password reset token, delete users, index and read private statuses and chats)" + }, + %{ + key: :moderator_privileges, + type: {:list, :atom}, + suggestions: [], + description: "What extra priviledges to allow moderators (e.g. updating user credentials, get password reset token, delete users, index and read private statuses and chats)" + }, + %{ key: :birthday_required, type: :boolean, description: "Require users to enter their birthday." diff --git a/lib/pleroma/web/plugs/ensure_privileged_plug.ex b/lib/pleroma/web/plugs/ensure_privileged_plug.ex @@ -0,0 +1,44 @@ +# Pleroma: A lightweight social networking server +# Copyright © 2017-2022 Pleroma Authors <https://pleroma.social/> +# SPDX-License-Identifier: AGPL-3.0-only + +defmodule Pleroma.Web.Plugs.EnsurePrivilegedPlug do + @moduledoc """ + Ensures staff are privileged enough to do certain tasks. + """ + import Pleroma.Web.TranslationHelpers + import Plug.Conn + + alias Pleroma.Config + alias Pleroma.User + + def init(options) do + options + end + + def call(%{assigns: %{user: %User{is_admin: false, is_moderator: false}}} = conn, _) do + conn + |> render_error(:forbidden, "User isn't privileged.") + |> halt() + end + + def call( + %{assigns: %{user: %User{is_admin: is_admin, is_moderator: is_moderator}}} = conn, + priviledge + ) do + if (is_admin and priviledge in Config.get([:instance, :admin_privileges])) or + (is_moderator and priviledge in Config.get([:instance, :moderator_privileges])) do + conn + else + conn + |> render_error(:forbidden, "User isn't privileged.") + |> halt() + end + end + + def call(conn, _) do + conn + |> render_error(:forbidden, "User isn't privileged.") + |> halt() + end +end diff --git a/test/pleroma/web/plugs/ensure_privileged_plug_test.exs b/test/pleroma/web/plugs/ensure_privileged_plug_test.exs @@ -0,0 +1,96 @@ +# Pleroma: A lightweight social networking server +# Copyright © 2017-2022 Pleroma Authors <https://pleroma.social/> +# SPDX-License-Identifier: AGPL-3.0-only + +defmodule Pleroma.Web.Plugs.EnsurePrivilegedPlugTest do + use Pleroma.Web.ConnCase, async: true + + alias Pleroma.Web.Plugs.EnsurePrivilegedPlug + import Pleroma.Factory + + test "denies a user that isn't moderator or admin" do + clear_config([:instance, :admin_privileges], []) + user = insert(:user) + + conn = + build_conn() + |> assign(:user, user) + |> EnsurePrivilegedPlug.call(:cofe) + + assert conn.status == 403 + end + + test "accepts an admin that is privileged" do + clear_config([:instance, :admin_privileges], [:cofe]) + user = insert(:user, is_admin: true) + conn = assign(build_conn(), :user, user) + + ret_conn = EnsurePrivilegedPlug.call(conn, :cofe) + + assert conn == ret_conn + end + + test "denies an admin that isn't privileged" do + clear_config([:instance, :admin_privileges], [:suya]) + user = insert(:user, is_admin: true) + + conn = + build_conn() + |> assign(:user, user) + |> EnsurePrivilegedPlug.call(:cofe) + + assert conn.status == 403 + end + + test "accepts a moderator that is privileged" do + clear_config([:instance, :moderator_privileges], [:cofe]) + user = insert(:user, is_moderator: true) + conn = assign(build_conn(), :user, user) + + ret_conn = EnsurePrivilegedPlug.call(conn, :cofe) + + assert conn == ret_conn + end + + test "denies a moderator that isn't privileged" do + clear_config([:instance, :moderator_privileges], [:suya]) + user = insert(:user, is_moderator: true) + + conn = + build_conn() + |> assign(:user, user) + |> EnsurePrivilegedPlug.call(:cofe) + + assert conn.status == 403 + end + + test "accepts for a priviledged role even if other role isn't priviledged" do + clear_config([:instance, :admin_privileges], [:cofe]) + clear_config([:instance, :moderator_privileges], []) + user = insert(:user, is_admin: true, is_moderator: true) + conn = assign(build_conn(), :user, user) + + ret_conn = EnsurePrivilegedPlug.call(conn, :cofe) + + # priviledged through admin role + assert conn == ret_conn + + clear_config([:instance, :admin_privileges], []) + clear_config([:instance, :moderator_privileges], [:cofe]) + user = insert(:user, is_admin: true, is_moderator: true) + conn = assign(build_conn(), :user, user) + + ret_conn = EnsurePrivilegedPlug.call(conn, :cofe) + + # priviledged through moderator role + assert conn == ret_conn + end + + test "denies when no user is set" do + conn = + build_conn() + |> EnsurePrivilegedPlug.call(:cofe) + + assert conn.status == 403 + end +end