diff options
author | Egor Kislitsyn <egor@kislitsyn.com> | 2019-10-30 18:21:49 +0700 |
---|---|---|
committer | Egor Kislitsyn <egor@kislitsyn.com> | 2019-10-30 18:21:49 +0700 |
commit | 61fc739ab8917ccb5a12d6ab6db6130dc231990b (patch) | |
tree | cbcf5d0b5c1f0f772bfbb301ebfe4bf0a59b4913 /lib | |
parent | 42708610857dd4aea1f488a31c1690cd37797333 (diff) | |
download | pleroma-61fc739ab8917ccb5a12d6ab6db6130dc231990b.tar.gz |
Handle "Move" activity
Diffstat (limited to 'lib')
-rw-r--r-- | lib/pleroma/following_relationship.ex | 24 | ||||
-rw-r--r-- | lib/pleroma/web/activity_pub/activity_pub.ex | 24 | ||||
-rw-r--r-- | lib/pleroma/web/activity_pub/transmogrifier.ex | 18 | ||||
-rw-r--r-- | lib/pleroma/web/activity_pub/visibility.ex | 1 | ||||
-rw-r--r-- | lib/pleroma/workers/background_worker.ex | 7 |
5 files changed, 74 insertions, 0 deletions
diff --git a/lib/pleroma/following_relationship.ex b/lib/pleroma/following_relationship.ex index 2ffac17ee..2f89eb4cf 100644 --- a/lib/pleroma/following_relationship.ex +++ b/lib/pleroma/following_relationship.ex @@ -107,4 +107,28 @@ defmodule Pleroma.FollowingRelationship do [user.follower_address | following] end end + + def move_following(origin, target) do + following_relationships = + __MODULE__ + |> where(following_id: ^origin.id) + |> preload([:follower]) + |> limit(50) + |> Repo.all() + + case following_relationships do + [] -> + :ok + + following_relationships -> + Enum.each(following_relationships, fn following_relationship -> + Repo.transaction(fn -> + Repo.delete(following_relationship) + User.follow(following_relationship.follower, target) + end) + end) + + move_following(origin, target) + end + end end diff --git a/lib/pleroma/web/activity_pub/activity_pub.ex b/lib/pleroma/web/activity_pub/activity_pub.ex index 6adadacdc..67c2cb659 100644 --- a/lib/pleroma/web/activity_pub/activity_pub.ex +++ b/lib/pleroma/web/activity_pub/activity_pub.ex @@ -514,6 +514,30 @@ defmodule Pleroma.Web.ActivityPub.ActivityPub do end end + def move(%User{} = origin, %User{} = target, local \\ true) do + params = %{ + "type" => "Move", + "actor" => origin.ap_id, + "object" => origin.ap_id, + "target" => target.ap_id + } + + with true <- origin.ap_id in target.also_known_as, + {:ok, activity} <- insert(params, local) do + maybe_federate(activity) + + BackgroundWorker.enqueue("move_following", %{ + "origin_id" => origin.id, + "target_id" => target.id + }) + + {:ok, activity} + else + false -> {:error, "Target account must have the origin in `alsoKnownAs`"} + err -> err + end + end + defp fetch_activities_for_context_query(context, opts) do public = [Pleroma.Constants.as_public()] diff --git a/lib/pleroma/web/activity_pub/transmogrifier.ex b/lib/pleroma/web/activity_pub/transmogrifier.ex index c23f2dcd0..78ee6192a 100644 --- a/lib/pleroma/web/activity_pub/transmogrifier.ex +++ b/lib/pleroma/web/activity_pub/transmogrifier.ex @@ -785,6 +785,24 @@ defmodule Pleroma.Web.ActivityPub.Transmogrifier do end end + def handle_incoming( + %{ + "type" => "Move", + "actor" => origin_actor, + "object" => origin_actor, + "target" => target_actor + }, + _options + ) do + with %User{} = origin_user <- User.get_cached_by_ap_id(origin_actor), + {:ok, %User{} = target_user} <- User.get_or_fetch_by_ap_id(target_actor), + true <- origin_actor in target_user.also_known_as do + ActivityPub.move(origin_user, target_user, false) + else + _e -> :error + end + end + def handle_incoming(_, _), do: :error @spec get_obj_helper(String.t(), Keyword.t()) :: {:ok, Object.t()} | nil diff --git a/lib/pleroma/web/activity_pub/visibility.ex b/lib/pleroma/web/activity_pub/visibility.ex index cd4097493..e172f6d3f 100644 --- a/lib/pleroma/web/activity_pub/visibility.ex +++ b/lib/pleroma/web/activity_pub/visibility.ex @@ -14,6 +14,7 @@ defmodule Pleroma.Web.ActivityPub.Visibility do @spec is_public?(Object.t() | Activity.t() | map()) :: boolean() def is_public?(%Object{data: %{"type" => "Tombstone"}}), do: false def is_public?(%Object{data: data}), do: is_public?(data) + def is_public?(%Activity{data: %{"type" => "Move"}}), do: true def is_public?(%Activity{data: data}), do: is_public?(data) def is_public?(%{"directMessage" => true}), do: false def is_public?(data), do: Utils.label_in_message?(Pleroma.Constants.as_public(), data) diff --git a/lib/pleroma/workers/background_worker.ex b/lib/pleroma/workers/background_worker.ex index 7ffc8eabe..323a4da1e 100644 --- a/lib/pleroma/workers/background_worker.ex +++ b/lib/pleroma/workers/background_worker.ex @@ -71,4 +71,11 @@ defmodule Pleroma.Workers.BackgroundWorker do activity = Activity.get_by_id(activity_id) Pleroma.Web.RichMedia.Helpers.perform(:fetch, activity) end + + def perform(%{"op" => "move_following", "origin_id" => origin_id, "target_id" => target_id}, _) do + origin = User.get_cached_by_id(origin_id) + target = User.get_cached_by_id(target_id) + + Pleroma.FollowingRelationship.move_following(origin, target) + end end |