Merge branch 'feature/invites' into 'develop'
[akkoma] / lib / pleroma / web / activity_pub / transmogrifier.ex
index 30cd70fb656096df97ee86fe285d8fbe3a174dc3..2ebc526df9dda0e264041725618f32923aaae6ee 100644 (file)
@@ -13,12 +13,25 @@ defmodule Pleroma.Web.ActivityPub.Transmogrifier do
 
   require Logger
 
+  def get_actor(%{"actor" => actor}) when is_binary(actor) do
+    actor
+  end
+
+  def get_actor(%{"actor" => actor}) when is_list(actor) do
+    Enum.at(actor, 0)
+  end
+
+  def get_actor(%{"actor" => actor_list}) do
+    Enum.find(actor_list, fn %{"type" => type} -> type == "Person" end)
+    |> Map.get("id")
+  end
+
   @doc """
   Modifies an incoming AP object (mastodon format) to our internal format.
   """
   def fix_object(object) do
     object
-    |> Map.put("actor", object["attributedTo"])
+    |> fix_actor
     |> fix_attachments
     |> fix_context
     |> fix_in_reply_to
@@ -27,6 +40,11 @@ defmodule Pleroma.Web.ActivityPub.Transmogrifier do
     |> fix_content_map
   end
 
+  def fix_actor(%{"attributedTo" => actor} = object) do
+    object
+    |> Map.put("actor", get_actor(%{"actor" => actor}))
+  end
+
   def fix_in_reply_to(%{"inReplyTo" => in_reply_to_id} = object)
       when not is_nil(in_reply_to_id) do
     case ActivityPub.fetch_object_from_id(in_reply_to_id) do
@@ -122,7 +140,11 @@ defmodule Pleroma.Web.ActivityPub.Transmogrifier do
   # TODO: validate those with a Ecto scheme
   # - tags
   # - emoji
-  def handle_incoming(%{"type" => "Create", "object" => %{"type" => "Note"} = object} = data) do
+  def handle_incoming(%{"type" => "Create", "object" => %{"type" => objtype} = object} = data)
+      when objtype in ["Article", "Note"] do
+    actor = get_actor(data)
+    data = Map.put(data, "actor", actor)
+
     with nil <- Activity.get_create_activity_by_object_ap_id(object["id"]),
          %User{} = user <- User.get_or_fetch_by_ap_id(data["actor"]) do
       object = fix_object(data["object"])
@@ -412,7 +434,7 @@ defmodule Pleroma.Web.ActivityPub.Transmogrifier do
   def handle_incoming(_), do: :error
 
   def get_obj_helper(id) do
-    if object = Object.get_by_ap_id(id), do: {:ok, object}, else: nil
+    if object = Object.normalize(id), do: {:ok, object}, else: nil
   end
 
   def set_reply_to_uri(%{"inReplyTo" => inReplyTo} = object) do
@@ -460,14 +482,7 @@ defmodule Pleroma.Web.ActivityPub.Transmogrifier do
   # Mastodon Accept/Reject requires a non-normalized object containing the actor URIs,
   # because of course it does.
   def prepare_outgoing(%{"type" => "Accept"} = data) do
-    follow_activity_id =
-      if is_binary(data["object"]) do
-        data["object"]
-      else
-        data["object"]["id"]
-      end
-
-    with follow_activity <- Activity.get_by_ap_id(follow_activity_id) do
+    with follow_activity <- Activity.normalize(data["object"]) do
       object = %{
         "actor" => follow_activity.actor,
         "object" => follow_activity.data["object"],
@@ -485,14 +500,7 @@ defmodule Pleroma.Web.ActivityPub.Transmogrifier do
   end
 
   def prepare_outgoing(%{"type" => "Reject"} = data) do
-    follow_activity_id =
-      if is_binary(data["object"]) do
-        data["object"]
-      else
-        data["object"]["id"]
-      end
-
-    with follow_activity <- Activity.get_by_ap_id(follow_activity_id) do
+    with follow_activity <- Activity.normalize(data["object"]) do
       object = %{
         "actor" => follow_activity.actor,
         "object" => follow_activity.data["object"],