mandate published on notes
[akkoma] / lib / pleroma / moderation_log.ex
index 142dd8e0a404300a0fefae72d2301a77acb3d888..7da8d0c633cd224c87f5e75aa093bd83c0c9fca2 100644 (file)
@@ -1,5 +1,5 @@
 # Pleroma: A lightweight social networking server
-# Copyright © 2017-2020 Pleroma Authors <https://pleroma.social/>
+# Copyright © 2017-2021 Pleroma Authors <https://pleroma.social/>
 # SPDX-License-Identifier: AGPL-3.0-only
 
 defmodule Pleroma.ModerationLog do
@@ -12,6 +12,26 @@ defmodule Pleroma.ModerationLog do
 
   import Ecto.Query
 
+  @type t :: %__MODULE__{}
+  @type log_subject :: Activity.t() | User.t() | list(User.t())
+  @type log_params :: %{
+          required(:actor) => User.t(),
+          required(:action) => String.t(),
+          optional(:subject) => log_subject(),
+          optional(:subject_actor) => User.t(),
+          optional(:subject_id) => String.t(),
+          optional(:subjects) => list(User.t()),
+          optional(:permission) => String.t(),
+          optional(:text) => String.t(),
+          optional(:sensitive) => String.t(),
+          optional(:visibility) => String.t(),
+          optional(:followed) => User.t(),
+          optional(:follower) => User.t(),
+          optional(:nicknames) => list(String.t()),
+          optional(:tags) => list(String.t()),
+          optional(:target) => String.t()
+        }
+
   schema "moderation_log" do
     field(:data, :map)
 
@@ -90,203 +110,105 @@ defmodule Pleroma.ModerationLog do
     parsed_datetime
   end
 
-  @spec insert_log(%{actor: User, subject: [User], action: String.t(), permission: String.t()}) ::
-          {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{
-        actor: %User{} = actor,
-        subject: subjects,
-        action: action,
-        permission: permission
-      }) do
-    %ModerationLog{
-      data: %{
-        "actor" => user_to_map(actor),
-        "subject" => user_to_map(subjects),
-        "action" => action,
-        "permission" => permission,
-        "message" => ""
-      }
-    }
-    |> insert_log_entry_with_message()
-  end
-
-  @spec insert_log(%{actor: User, subject: User, action: String.t()}) ::
-          {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{
-        actor: %User{} = actor,
-        action: "report_update",
-        subject: %Activity{data: %{"type" => "Flag"}} = subject
-      }) do
-    %ModerationLog{
-      data: %{
-        "actor" => user_to_map(actor),
-        "action" => "report_update",
-        "subject" => report_to_map(subject),
-        "message" => ""
-      }
+  defp prepare_log_data(%{actor: actor, action: action} = attrs) do
+    %{
+      "actor" => user_to_map(actor),
+      "action" => action,
+      "message" => ""
     }
-    |> insert_log_entry_with_message()
-  end
+    |> Pleroma.Maps.put_if_present("subject_actor", user_to_map(attrs[:subject_actor]))
+  end
+
+  defp prepare_log_data(attrs), do: attrs
+
+  @spec insert_log(log_params()) :: {:ok, ModerationLog} | {:error, any}
+  def insert_log(%{actor: %User{}, subject: subjects, permission: permission} = attrs) do
+    data =
+      attrs
+      |> prepare_log_data
+      |> Map.merge(%{"subject" => user_to_map(subjects), "permission" => permission})
+
+    insert_log_entry_with_message(%ModerationLog{data: data})
+  end
+
+  def insert_log(%{actor: %User{}, action: action, subject: %Activity{} = subject} = attrs)
+      when action in ["report_note_delete", "report_update", "report_note"] do
+    data =
+      attrs
+      |> prepare_log_data
+      |> Pleroma.Maps.put_if_present("text", attrs[:text])
+      |> Map.merge(%{"subject" => report_to_map(subject)})
+
+    insert_log_entry_with_message(%ModerationLog{data: data})
+  end
+
+  def insert_log(
+        %{
+          actor: %User{},
+          action: action,
+          subject: %Activity{} = subject,
+          sensitive: sensitive,
+          visibility: visibility
+        } = attrs
+      )
+      when action == "status_update" do
+    data =
+      attrs
+      |> prepare_log_data
+      |> Map.merge(%{
+        "subject" => status_to_map(subject),
+        "sensitive" => sensitive,
+        "visibility" => visibility
+      })
 
-  @spec insert_log(%{actor: User, subject: Activity, action: String.t(), text: String.t()}) ::
-          {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{
-        actor: %User{} = actor,
-        action: "report_note",
-        subject: %Activity{} = subject,
-        text: text
-      }) do
-    %ModerationLog{
-      data: %{
-        "actor" => user_to_map(actor),
-        "action" => "report_note",
-        "subject" => report_to_map(subject),
-        "text" => text
-      }
-    }
-    |> insert_log_entry_with_message()
+    insert_log_entry_with_message(%ModerationLog{data: data})
   end
 
-  @spec insert_log(%{actor: User, subject: Activity, action: String.t(), text: String.t()}) ::
-          {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{
-        actor: %User{} = actor,
-        action: "report_note_delete",
-        subject: %Activity{} = subject,
-        text: text
-      }) do
-    %ModerationLog{
-      data: %{
-        "actor" => user_to_map(actor),
-        "action" => "report_note_delete",
-        "subject" => report_to_map(subject),
-        "text" => text
-      }
-    }
-    |> insert_log_entry_with_message()
-  end
+  def insert_log(%{actor: %User{}, action: action, subject_id: subject_id} = attrs)
+      when action == "status_delete" do
+    data =
+      attrs
+      |> prepare_log_data
+      |> Map.merge(%{"subject_id" => subject_id})
 
-  @spec insert_log(%{
-          actor: User,
-          subject: Activity,
-          action: String.t(),
-          sensitive: String.t(),
-          visibility: String.t()
-        }) :: {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{
-        actor: %User{} = actor,
-        action: "status_update",
-        subject: %Activity{} = subject,
-        sensitive: sensitive,
-        visibility: visibility
-      }) do
-    %ModerationLog{
-      data: %{
-        "actor" => user_to_map(actor),
-        "action" => "status_update",
-        "subject" => status_to_map(subject),
-        "sensitive" => sensitive,
-        "visibility" => visibility,
-        "message" => ""
-      }
-    }
-    |> insert_log_entry_with_message()
+    insert_log_entry_with_message(%ModerationLog{data: data})
   end
 
-  @spec insert_log(%{actor: User, action: String.t(), subject_id: String.t()}) ::
-          {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{
-        actor: %User{} = actor,
-        action: "status_delete",
-        subject_id: subject_id
-      }) do
-    %ModerationLog{
-      data: %{
-        "actor" => user_to_map(actor),
-        "action" => "status_delete",
-        "subject_id" => subject_id,
-        "message" => ""
-      }
-    }
-    |> insert_log_entry_with_message()
-  end
+  def insert_log(%{actor: %User{}, subject: subject, action: _action} = attrs) do
+    data =
+      attrs
+      |> prepare_log_data
+      |> Map.merge(%{"subject" => user_to_map(subject)})
 
-  @spec insert_log(%{actor: User, subject: User, action: String.t()}) ::
-          {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{actor: %User{} = actor, subject: subject, action: action}) do
-    %ModerationLog{
-      data: %{
-        "actor" => user_to_map(actor),
-        "action" => action,
-        "subject" => user_to_map(subject),
-        "message" => ""
-      }
-    }
-    |> insert_log_entry_with_message()
+    insert_log_entry_with_message(%ModerationLog{data: data})
   end
 
-  @spec insert_log(%{actor: User, subjects: [User], action: String.t()}) ::
-          {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{actor: %User{} = actor, subjects: subjects, action: action}) do
-    subjects = Enum.map(subjects, &user_to_map/1)
+  def insert_log(%{actor: %User{}, subjects: subjects, action: _action} = attrs) do
+    data =
+      attrs
+      |> prepare_log_data
+      |> Map.merge(%{"subjects" => user_to_map(subjects)})
 
-    %ModerationLog{
-      data: %{
-        "actor" => user_to_map(actor),
-        "action" => action,
-        "subjects" => subjects,
-        "message" => ""
-      }
-    }
-    |> insert_log_entry_with_message()
+    insert_log_entry_with_message(%ModerationLog{data: data})
   end
 
-  @spec insert_log(%{actor: User, action: String.t(), followed: User, follower: User}) ::
-          {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{
-        actor: %User{} = actor,
-        followed: %User{} = followed,
-        follower: %User{} = follower,
-        action: "follow"
-      }) do
-    %ModerationLog{
-      data: %{
-        "actor" => user_to_map(actor),
-        "action" => "follow",
-        "followed" => user_to_map(followed),
-        "follower" => user_to_map(follower),
-        "message" => ""
-      }
-    }
-    |> insert_log_entry_with_message()
-  end
+  def insert_log(
+        %{
+          actor: %User{},
+          followed: %User{} = followed,
+          follower: %User{} = follower,
+          action: action
+        } = attrs
+      )
+      when action in ["unfollow", "follow"] do
+    data =
+      attrs
+      |> prepare_log_data
+      |> Map.merge(%{"followed" => user_to_map(followed), "follower" => user_to_map(follower)})
 
-  @spec insert_log(%{actor: User, action: String.t(), followed: User, follower: User}) ::
-          {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{
-        actor: %User{} = actor,
-        followed: %User{} = followed,
-        follower: %User{} = follower,
-        action: "unfollow"
-      }) do
-    %ModerationLog{
-      data: %{
-        "actor" => user_to_map(actor),
-        "action" => "unfollow",
-        "followed" => user_to_map(followed),
-        "follower" => user_to_map(follower),
-        "message" => ""
-      }
-    }
-    |> insert_log_entry_with_message()
+    insert_log_entry_with_message(%ModerationLog{data: data})
   end
 
-  @spec insert_log(%{
-          actor: User,
-          action: String.t(),
-          nicknames: [String.t()],
-          tags: [String.t()]
-        }) :: {:ok, ModerationLog} | {:error, any}
   def insert_log(%{
         actor: %User{} = actor,
         nicknames: nicknames,
@@ -305,36 +227,14 @@ defmodule Pleroma.ModerationLog do
     |> insert_log_entry_with_message()
   end
 
-  @spec insert_log(%{actor: User, action: String.t(), target: String.t()}) ::
-          {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{
-        actor: %User{} = actor,
-        action: action,
-        target: target
-      })
+  def insert_log(%{actor: %User{}, action: action, target: target} = attrs)
       when action in ["relay_follow", "relay_unfollow"] do
-    %ModerationLog{
-      data: %{
-        "actor" => user_to_map(actor),
-        "action" => action,
-        "target" => target,
-        "message" => ""
-      }
-    }
-    |> insert_log_entry_with_message()
-  end
+    data =
+      attrs
+      |> prepare_log_data
+      |> Map.merge(%{"target" => target})
 
-  @spec insert_log(%{actor: User, action: String.t(), subject_id: String.t()}) ::
-          {:ok, ModerationLog} | {:error, any}
-  def insert_log(%{actor: %User{} = actor, action: "chat_message_delete", subject_id: subject_id}) do
-    %ModerationLog{
-      data: %{
-        "actor" => %{"nickname" => actor.nickname},
-        "action" => "chat_message_delete",
-        "subject_id" => subject_id
-      }
-    }
-    |> insert_log_entry_with_message()
+    insert_log_entry_with_message(%ModerationLog{data: data})
   end
 
   @spec insert_log_entry_with_message(ModerationLog) :: {:ok, ModerationLog} | {:error, any}
@@ -345,32 +245,27 @@ defmodule Pleroma.ModerationLog do
   end
 
   defp user_to_map(users) when is_list(users) do
-    users |> Enum.map(&user_to_map/1)
+    Enum.map(users, &user_to_map/1)
   end
 
   defp user_to_map(%User{} = user) do
     user
-    |> Map.from_struct()
     |> Map.take([:id, :nickname])
     |> Map.new(fn {k, v} -> {Atom.to_string(k), v} end)
     |> Map.put("type", "user")
   end
 
+  defp user_to_map(_), do: nil
+
   defp report_to_map(%Activity{} = report) do
-    %{
-      "type" => "report",
-      "id" => report.id,
-      "state" => report.data["state"]
-    }
+    %{"type" => "report", "id" => report.id, "state" => report.data["state"]}
   end
 
   defp status_to_map(%Activity{} = status) do
-    %{
-      "type" => "status",
-      "id" => status.id
-    }
+    %{"type" => "status", "id" => status.id}
   end
 
+  @spec get_log_entry_message(ModerationLog.t()) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -382,7 +277,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} made @#{follower_nickname} #{action} @#{followed_nickname}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -393,7 +287,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} deleted users: #{users_to_nicknames_string(subjects)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -404,7 +297,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} created users: #{users_to_nicknames_string(subjects)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -415,7 +307,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} activated users: #{users_to_nicknames_string(users)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -426,7 +317,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} deactivated users: #{users_to_nicknames_string(users)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -437,7 +327,26 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} approved users: #{users_to_nicknames_string(users)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
+  def get_log_entry_message(%ModerationLog{
+        data: %{
+          "actor" => %{"nickname" => actor_nickname},
+          "action" => "add_suggestion",
+          "subject" => users
+        }
+      }) do
+    "@#{actor_nickname} added suggested users: #{users_to_nicknames_string(users)}"
+  end
+
+  def get_log_entry_message(%ModerationLog{
+        data: %{
+          "actor" => %{"nickname" => actor_nickname},
+          "action" => "remove_suggestion",
+          "subject" => users
+        }
+      }) do
+    "@#{actor_nickname} removed suggested users: #{users_to_nicknames_string(users)}"
+  end
+
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -451,7 +360,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} added tags: #{tags_string} to users: #{nicknames_to_string(nicknames)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -465,7 +373,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} removed tags: #{tags_string} from users: #{nicknames_to_string(nicknames)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -477,7 +384,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} made #{users_to_nicknames_string(users)} #{permission}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -489,7 +395,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} revoked #{permission} role from #{users_to_nicknames_string(users)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -500,7 +405,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} followed relay: #{target}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -511,42 +415,48 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} unfollowed relay: #{target}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
-  def get_log_entry_message(%ModerationLog{
-        data: %{
-          "actor" => %{"nickname" => actor_nickname},
-          "action" => "report_update",
-          "subject" => %{"id" => subject_id, "state" => state, "type" => "report"}
-        }
-      }) do
-    "@#{actor_nickname} updated report ##{subject_id} with '#{state}' state"
-  end
-
-  @spec get_log_entry_message(ModerationLog) :: String.t()
-  def get_log_entry_message(%ModerationLog{
-        data: %{
-          "actor" => %{"nickname" => actor_nickname},
-          "action" => "report_note",
-          "subject" => %{"id" => subject_id, "type" => "report"},
-          "text" => text
-        }
-      }) do
-    "@#{actor_nickname} added note '#{text}' to report ##{subject_id}"
-  end
-
-  @spec get_log_entry_message(ModerationLog) :: String.t()
-  def get_log_entry_message(%ModerationLog{
-        data: %{
-          "actor" => %{"nickname" => actor_nickname},
-          "action" => "report_note_delete",
-          "subject" => %{"id" => subject_id, "type" => "report"},
-          "text" => text
-        }
-      }) do
-    "@#{actor_nickname} deleted note '#{text}' from report ##{subject_id}"
+  def get_log_entry_message(
+        %ModerationLog{
+          data: %{
+            "actor" => %{"nickname" => actor_nickname},
+            "action" => "report_update",
+            "subject" => %{"id" => subject_id, "state" => state, "type" => "report"}
+          }
+        } = log
+      ) do
+    "@#{actor_nickname} updated report ##{subject_id}" <>
+      subject_actor_nickname(log, " (on user ", ")") <>
+      " with '#{state}' state"
+  end
+
+  def get_log_entry_message(
+        %ModerationLog{
+          data: %{
+            "actor" => %{"nickname" => actor_nickname},
+            "action" => "report_note",
+            "subject" => %{"id" => subject_id, "type" => "report"},
+            "text" => text
+          }
+        } = log
+      ) do
+    "@#{actor_nickname} added note '#{text}' to report ##{subject_id}" <>
+      subject_actor_nickname(log, " on user ")
+  end
+
+  def get_log_entry_message(
+        %ModerationLog{
+          data: %{
+            "actor" => %{"nickname" => actor_nickname},
+            "action" => "report_note_delete",
+            "subject" => %{"id" => subject_id, "type" => "report"},
+            "text" => text
+          }
+        } = log
+      ) do
+    "@#{actor_nickname} deleted note '#{text}' from report ##{subject_id}" <>
+      subject_actor_nickname(log, " on user ")
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -559,7 +469,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} updated status ##{subject_id}, set visibility: '#{visibility}'"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -572,7 +481,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} updated status ##{subject_id}, set sensitive: '#{sensitive}'"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -582,12 +490,9 @@ defmodule Pleroma.ModerationLog do
           "visibility" => visibility
         }
       }) do
-    "@#{actor_nickname} updated status ##{subject_id}, set sensitive: '#{sensitive}', visibility: '#{
-      visibility
-    }'"
+    "@#{actor_nickname} updated status ##{subject_id}, set sensitive: '#{sensitive}', visibility: '#{visibility}'"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -598,7 +503,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} deleted status ##{subject_id}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -609,7 +513,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} forced password reset for users: #{users_to_nicknames_string(subjects)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -620,7 +523,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} confirmed email for users: #{users_to_nicknames_string(subjects)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -628,12 +530,9 @@ defmodule Pleroma.ModerationLog do
           "subject" => subjects
         }
       }) do
-    "@#{actor_nickname} re-sent confirmation email for users: #{
-      users_to_nicknames_string(subjects)
-    }"
+    "@#{actor_nickname} re-sent confirmation email for users: #{users_to_nicknames_string(subjects)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -644,17 +543,6 @@ defmodule Pleroma.ModerationLog do
     "@#{actor_nickname} updated users: #{users_to_nicknames_string(subjects)}"
   end
 
-  @spec get_log_entry_message(ModerationLog) :: String.t()
-  def get_log_entry_message(%ModerationLog{
-        data: %{
-          "actor" => %{"nickname" => actor_nickname},
-          "action" => "chat_message_delete",
-          "subject_id" => subject_id
-        }
-      }) do
-    "@#{actor_nickname} deleted chat message ##{subject_id}"
-  end
-
   def get_log_entry_message(%ModerationLog{
         data: %{
           "actor" => %{"nickname" => actor_nickname},
@@ -676,4 +564,16 @@ defmodule Pleroma.ModerationLog do
     |> Enum.map(&"@#{&1["nickname"]}")
     |> Enum.join(", ")
   end
+
+  defp subject_actor_nickname(%ModerationLog{data: data}, prefix_msg, postfix_msg \\ "") do
+    case data do
+      %{"subject_actor" => %{"nickname" => subject_actor}} ->
+        [prefix_msg, "@#{subject_actor}", postfix_msg]
+        |> Enum.reject(&(&1 == ""))
+        |> Enum.join()
+
+      _ ->
+        ""
+    end
+  end
 end