From 654a41b2c92acf7fe462c5452fc36d408e32b494 Mon Sep 17 00:00:00 2001 From: Lain Soykaf Date: Sat, 31 Oct 2026 15:37:41 +0400 Subject: [PATCH] fix(activitypub): accept emoji reactions with a single tag object Ported from Akkoma 462225880. Co-authored-by: Oneric --- changelog.d/emoji-react-single-tag.fix | 1 + .../emoji_react_validator.ex | 6 ++++- .../emoji_react_handling_test.exs | 25 +++++++++++++++++++ 3 files changed, 31 insertions(+), 1 deletion(-) create mode 100644 changelog.d/emoji-react-single-tag.fix diff --git a/changelog.d/emoji-react-single-tag.fix b/changelog.d/emoji-react-single-tag.fix new file mode 100644 index 000000000..565775830 --- /dev/null +++ b/changelog.d/emoji-react-single-tag.fix @@ -0,0 +1 @@ +Accept incoming emoji reactions whose tag is a single object instead of an array diff --git a/lib/pleroma/web/activity_pub/object_validators/emoji_react_validator.ex b/lib/pleroma/web/activity_pub/object_validators/emoji_react_validator.ex index 65ba047e6..b7197c3f3 100644 --- a/lib/pleroma/web/activity_pub/object_validators/emoji_react_validator.ex +++ b/lib/pleroma/web/activity_pub/object_validators/emoji_react_validator.ex @@ -57,7 +57,7 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.EmojiReactValidator do |> CommonFixes.fix_actor() |> CommonFixes.fix_activity_addressing() - data = Map.put_new(data, "tag", []) + data = fix_tag(data) case Object.normalize(data["object"]) do %Object{} = object -> @@ -70,6 +70,10 @@ defmodule Pleroma.Web.ActivityPub.ObjectValidators.EmojiReactValidator do end end + # JSON-LD compaction turns a single-element array into a bare object + defp fix_tag(%{"tag" => %{} = tag} = data), do: Map.put(data, "tag", [tag]) + defp fix_tag(data), do: Map.put_new(data, "tag", []) + defp fix_emoji_qualification(%{"content" => emoji} = data) do new_emoji = Pleroma.Emoji.fully_qualify_emoji(emoji) diff --git a/test/pleroma/web/activity_pub/transmogrifier/emoji_react_handling_test.exs b/test/pleroma/web/activity_pub/transmogrifier/emoji_react_handling_test.exs index f2e1cefa3..2e1841559 100644 --- a/test/pleroma/web/activity_pub/transmogrifier/emoji_react_handling_test.exs +++ b/test/pleroma/web/activity_pub/transmogrifier/emoji_react_handling_test.exs @@ -86,6 +86,31 @@ defmodule Pleroma.Web.ActivityPub.Transmogrifier.EmojiReactHandlingTest do ) end + test "it works for incoming custom emoji reactions with a single tag object" do + user = insert(:user) + other_user = insert(:user, local: false) + {:ok, activity} = CommonAPI.post(user, %{status: "hello"}) + + data = + File.read!("test/fixtures/custom-emoji-reaction.json") + |> Jason.decode!() + |> Map.put("object", activity.data["object"]) + |> Map.put("actor", other_user.ap_id) + + [tag] = data["tag"] + data = Map.put(data, "tag", tag) + + {:ok, %Activity{data: data, local: false}} = Transmogrifier.handle_incoming(data) + + assert data["content"] == ":hanapog:" + assert [%{"name" => "hanapog"}] = data["tag"] + + object = Object.get_by_ap_id(data["object"]) + url = tag["icon"]["url"] + + assert match?([["hanapog", _, ^url]], object.data["reactions"]) + end + test "it works for incoming unqualified emoji reactions" do user = insert(:user) other_user = insert(:user, local: false)