don't persist undo of follows #149
3 changed files with 79 additions and 1 deletions
|
@ -327,7 +327,9 @@ def unfollow(follower, followed, activity_id \\ nil, local \\ true) do
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
defp do_unfollow(follower, followed, activity_id, local) do
|
defp do_unfollow(follower, followed, activity_id, local)
|
||||||
|
|
||||||
|
defp do_unfollow(follower, followed, activity_id, local) when local == true do
|
||||||
with %Activity{} = follow_activity <- fetch_latest_follow(follower, followed),
|
with %Activity{} = follow_activity <- fetch_latest_follow(follower, followed),
|
||||||
{:ok, follow_activity} <- update_follow_state(follow_activity, "cancelled"),
|
{:ok, follow_activity} <- update_follow_state(follow_activity, "cancelled"),
|
||||||
unfollow_data <- make_unfollow_data(follower, followed, follow_activity, activity_id),
|
unfollow_data <- make_unfollow_data(follower, followed, follow_activity, activity_id),
|
||||||
|
@ -341,6 +343,32 @@ defp do_unfollow(follower, followed, activity_id, local) do
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
defp do_unfollow(follower, followed, activity_id, false) do
|
||||||
|
# On a remote unfollow, _remove_ their activity from the database, since some software (MISSKEEEEY)
|
||||||
|
# uses deterministic ids for follows.
|
||||||
|
with %Activity{} = follow_activity <- fetch_latest_follow(follower, followed),
|
||||||
|
{:ok, _activity} <- Repo.delete(follow_activity),
|
||||||
|
unfollow_data <- make_unfollow_data(follower, followed, follow_activity, activity_id),
|
||||||
|
unfollow_activity <- remote_unfollow_data(unfollow_data),
|
||||||
|
_ <- notify_and_stream(unfollow_activity) do
|
||||||
|
{:ok, unfollow_activity}
|
||||||
|
else
|
||||||
|
nil -> nil
|
||||||
|
{:error, error} -> Repo.rollback(error)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
defp remote_unfollow_data(data) do
|
||||||
|
{recipients, _, _} = get_recipients(data)
|
||||||
|
|
||||||
|
%Activity{
|
||||||
|
data: data,
|
||||||
|
local: false,
|
||||||
|
actor: data["actor"],
|
||||||
|
recipients: recipients
|
||||||
|
}
|
||||||
|
end
|
||||||
|
|
||||||
@spec flag(map()) :: {:ok, Activity.t()} | {:error, any()}
|
@spec flag(map()) :: {:ok, Activity.t()} | {:error, any()}
|
||||||
def flag(params) do
|
def flag(params) do
|
||||||
with {:ok, result} <- Repo.transaction(fn -> do_flag(params) end) do
|
with {:ok, result} <- Repo.transaction(fn -> do_flag(params) end) do
|
||||||
|
|
|
@ -0,0 +1,35 @@
|
||||||
|
defmodule Pleroma.Repo.Migrations.RemoveRemoteCancelledFollowRequests do
|
||||||
|
use Ecto.Migration
|
||||||
|
|
||||||
|
def up do
|
||||||
|
statement = """
|
||||||
|
DELETE FROM
|
||||||
|
activities
|
||||||
|
WHERE
|
||||||
|
(data->>'type') = 'Follow'
|
||||||
|
AND
|
||||||
|
(data->>'state') = 'cancelled'
|
||||||
|
AND
|
||||||
|
local = false;
|
||||||
|
"""
|
||||||
|
|
||||||
|
execute(statement)
|
||||||
|
|
||||||
|
statement = """
|
||||||
|
DELETE FROM
|
||||||
|
activities
|
||||||
|
WHERE
|
||||||
|
(data->>'type') = 'Undo'
|
||||||
|
AND
|
||||||
|
(data->'object'->>'type') = 'Follow'
|
||||||
|
AND
|
||||||
|
local = false;
|
||||||
|
"""
|
||||||
|
|
||||||
|
execute(statement)
|
||||||
|
end
|
||||||
|
|
||||||
|
def down do
|
||||||
|
:ok
|
||||||
|
end
|
||||||
|
end
|
|
@ -1375,6 +1375,21 @@ test "creates an undo activity for a pending follow request" do
|
||||||
assert embedded_object["object"] == followed.ap_id
|
assert embedded_object["object"] == followed.ap_id
|
||||||
assert embedded_object["id"] == follow_activity.data["id"]
|
assert embedded_object["id"] == follow_activity.data["id"]
|
||||||
end
|
end
|
||||||
|
|
||||||
|
test "it removes the follow activity if it was remote" do
|
||||||
|
follower = insert(:user, local: false)
|
||||||
|
followed = insert(:user)
|
||||||
|
|
||||||
|
{:ok, _, _, follow_activity} = CommonAPI.follow(follower, followed)
|
||||||
|
{:ok, activity} = ActivityPub.unfollow(follower, followed, nil, false)
|
||||||
|
|
||||||
|
assert activity.data["type"] == "Undo"
|
||||||
|
assert activity.data["actor"] == follower.ap_id
|
||||||
|
|
||||||
|
activity = Activity.get_by_id(follow_activity.id)
|
||||||
|
assert is_nil(activity)
|
||||||
|
assert is_nil(Utils.fetch_latest_follow(follower, followed))
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
describe "timeline post-processing" do
|
describe "timeline post-processing" do
|
||||||
|
|
Loading…
Reference in a new issue