Merge branch 'feature/create-tombstone-instead-of-delete' into 'develop'

Create tombstone instead of object deletion

See merge request pleroma/pleroma!593
This commit is contained in:
kaniini 2018-12-27 19:37:55 +00:00
commit bee6acd51d
9 changed files with 53 additions and 13 deletions

View file

@ -80,9 +80,8 @@ defmodule Pleroma.Notification do
end end
def clear(user) do def clear(user) do
query = from(n in Notification, where: n.user_id == ^user.id) from(n in Notification, where: n.user_id == ^user.id)
|> Repo.delete_all()
Repo.delete_all(query)
end end
def dismiss(%{id: user_id} = _user, id) do def dismiss(%{id: user_id} = _user, id) do

View file

@ -4,7 +4,7 @@
defmodule Pleroma.Object do defmodule Pleroma.Object do
use Ecto.Schema use Ecto.Schema
alias Pleroma.{Repo, Object, User, Activity} alias Pleroma.{Repo, Object, User, Activity, ObjectTombstone}
import Ecto.{Query, Changeset} import Ecto.{Query, Changeset}
schema "objects" do schema "objects" do
@ -66,8 +66,25 @@ defmodule Pleroma.Object do
Object.change(%Object{}, %{data: %{"id" => context}}) Object.change(%Object{}, %{data: %{"id" => context}})
end end
def make_tombstone(%Object{data: %{"id" => id, "type" => type}}, deleted \\ DateTime.utc_now()) do
%ObjectTombstone{
id: id,
formerType: type,
deleted: deleted
}
|> Map.from_struct()
end
def swap_object_with_tombstone(object) do
tombstone = make_tombstone(object)
object
|> Object.change(%{data: tombstone})
|> Repo.update()
end
def delete(%Object{data: %{"id" => id}} = object) do def delete(%Object{data: %{"id" => id}} = object) do
with Repo.delete(object), with {:ok, _obj} = swap_object_with_tombstone(object),
Repo.delete_all(Activity.all_non_create_by_object_ap_id_q(id)), Repo.delete_all(Activity.all_non_create_by_object_ap_id_q(id)),
{:ok, true} <- Cachex.del(:object_cache, "object:#{id}") do {:ok, true} <- Cachex.del(:object_cache, "object:#{id}") do
{:ok, object} {:ok, object}

View file

@ -0,0 +1,4 @@
defmodule Pleroma.ObjectTombstone do
@enforce_keys [:id, :formerType, :deleted]
defstruct [:id, :formerType, :deleted, type: "Tombstone"]
end

View file

@ -4,18 +4,19 @@
defmodule Pleroma.ActivityTest do defmodule Pleroma.ActivityTest do
use Pleroma.DataCase use Pleroma.DataCase
alias Pleroma.Activity
import Pleroma.Factory import Pleroma.Factory
test "returns an activity by it's AP id" do test "returns an activity by it's AP id" do
activity = insert(:note_activity) activity = insert(:note_activity)
found_activity = Pleroma.Activity.get_by_ap_id(activity.data["id"]) found_activity = Activity.get_by_ap_id(activity.data["id"])
assert activity == found_activity assert activity == found_activity
end end
test "returns activities by it's objects AP ids" do test "returns activities by it's objects AP ids" do
activity = insert(:note_activity) activity = insert(:note_activity)
[found_activity] = Pleroma.Activity.all_by_object_ap_id(activity.data["object"]["id"]) [found_activity] = Activity.all_by_object_ap_id(activity.data["object"]["id"])
assert activity == found_activity assert activity == found_activity
end end
@ -23,8 +24,7 @@ defmodule Pleroma.ActivityTest do
test "returns the activity that created an object" do test "returns the activity that created an object" do
activity = insert(:note_activity) activity = insert(:note_activity)
found_activity = found_activity = Activity.get_create_activity_by_object_ap_id(activity.data["object"]["id"])
Pleroma.Activity.get_create_activity_by_object_ap_id(activity.data["object"]["id"])
assert activity == found_activity assert activity == found_activity
end end

View file

@ -36,6 +36,8 @@ defmodule Pleroma.ObjectTest do
found_object = Object.get_by_ap_id(object.data["id"]) found_object = Object.get_by_ap_id(object.data["id"])
refute object == found_object refute object == found_object
assert found_object.data["type"] == "Tombstone"
end end
test "ensures cache is cleared for the object" do test "ensures cache is cleared for the object" do
@ -51,6 +53,8 @@ defmodule Pleroma.ObjectTest do
cached_object = Object.get_cached_by_ap_id(object.data["id"]) cached_object = Object.get_cached_by_ap_id(object.data["id"])
refute object == cached_object refute object == cached_object
assert cached_object.data["type"] == "Tombstone"
end end
end end
end end

View file

@ -492,7 +492,7 @@ defmodule Pleroma.Web.ActivityPub.ActivityPubTest do
assert Repo.get(Activity, delete.id) != nil assert Repo.get(Activity, delete.id) != nil
assert Repo.get(Object, object.id) == nil assert Repo.get(Object, object.id).data["type"] == "Tombstone"
end end
end end

View file

@ -296,7 +296,7 @@ defmodule Pleroma.Web.MastodonAPI.MastodonAPIControllerTest do
assert %{} = json_response(conn, 200) assert %{} = json_response(conn, 200)
assert Repo.get(Activity, activity.id) == nil refute Repo.get(Activity, activity.id)
end end
test "when you didn't create it", %{conn: conn} do test "when you didn't create it", %{conn: conn} do

View file

@ -25,7 +25,7 @@ defmodule Pleroma.Web.OStatus.DeleteHandlingTest do
refute Repo.get(Activity, note.id) refute Repo.get(Activity, note.id)
refute Repo.get(Activity, like.id) refute Repo.get(Activity, like.id)
refute Object.get_by_ap_id(note.data["object"]["id"]) assert Object.get_by_ap_id(note.data["object"]["id"]).data["type"] == "Tombstone"
assert Repo.get(Activity, second_note.id) assert Repo.get(Activity, second_note.id)
assert Object.get_by_ap_id(second_note.data["object"]["id"]) assert Object.get_by_ap_id(second_note.data["object"]["id"])

View file

@ -5,7 +5,7 @@
defmodule Pleroma.Web.OStatus.OStatusControllerTest do defmodule Pleroma.Web.OStatus.OStatusControllerTest do
use Pleroma.Web.ConnCase use Pleroma.Web.ConnCase
import Pleroma.Factory import Pleroma.Factory
alias Pleroma.{User, Repo} alias Pleroma.{User, Repo, Object}
alias Pleroma.Web.CommonAPI alias Pleroma.Web.CommonAPI
alias Pleroma.Web.OStatus.ActivityRepresenter alias Pleroma.Web.OStatus.ActivityRepresenter
@ -114,6 +114,22 @@ defmodule Pleroma.Web.OStatus.OStatusControllerTest do
|> response(404) |> response(404)
end end
test "404s on deleted objects", %{conn: conn} do
note_activity = insert(:note_activity)
[_, uuid] = hd(Regex.scan(~r/.+\/([\w-]+)$/, note_activity.data["object"]["id"]))
object = Object.get_by_ap_id(note_activity.data["object"]["id"])
conn
|> get("/objects/#{uuid}")
|> response(200)
Object.delete(object)
conn
|> get("/objects/#{uuid}")
|> response(404)
end
test "gets an activity", %{conn: conn} do test "gets an activity", %{conn: conn} do
note_activity = insert(:note_activity) note_activity = insert(:note_activity)
[_, uuid] = hd(Regex.scan(~r/.+\/([\w-]+)$/, note_activity.data["id"])) [_, uuid] = hd(Regex.scan(~r/.+\/([\w-]+)$/, note_activity.data["id"]))