fix(reports): remove on delete cascade for reports
Deleting an actor should not remove the reports Signed-off-by: Thomas Citharel <tcit@tcit.fr>
This commit is contained in:
parent
69588dbf4c
commit
4f530cabcf
70
lib/mobilizon/storage/views/instances.ex
Normal file
70
lib/mobilizon/storage/views/instances.ex
Normal file
|
@ -0,0 +1,70 @@
|
||||||
|
defmodule Mobilizon.Storage.Views.Instances do
|
||||||
|
@moduledoc """
|
||||||
|
SQL code for PostgreSQL instances materialized view
|
||||||
|
"""
|
||||||
|
|
||||||
|
def create_materialized_view do
|
||||||
|
"""
|
||||||
|
CREATE MATERIALIZED VIEW instances AS
|
||||||
|
SELECT
|
||||||
|
a.domain,
|
||||||
|
COUNT(DISTINCT(p.id)) AS person_count,
|
||||||
|
COUNT(DISTINCT(g.id)) AS group_count,
|
||||||
|
COUNT(DISTINCT(e.id)) AS event_count,
|
||||||
|
COUNT(f1.id) AS followers_count,
|
||||||
|
COUNT(f2.id) AS followings_count,
|
||||||
|
COUNT(r.id) AS reports_count,
|
||||||
|
SUM(COALESCE((m.file->>'size')::int, 0)) AS media_size
|
||||||
|
FROM actors a
|
||||||
|
LEFT JOIN actors p ON a.id = p.id AND p.type = 'Person'
|
||||||
|
LEFT JOIN actors g ON a.id = g.id AND g.type = 'Group'
|
||||||
|
LEFT JOIN events e ON a.id = e.organizer_actor_id
|
||||||
|
LEFT JOIN followers f1 ON a.id = f1.actor_id
|
||||||
|
LEFT JOIN followers f2 ON a.id = f2.target_actor_id
|
||||||
|
LEFT JOIN reports r ON r.reported_id = a.id
|
||||||
|
LEFT JOIN medias m ON m.actor_id = a.id
|
||||||
|
WHERE a.domain IS NOT NULL
|
||||||
|
GROUP BY a.domain;
|
||||||
|
"""
|
||||||
|
end
|
||||||
|
|
||||||
|
def refresh_instances do
|
||||||
|
"""
|
||||||
|
CREATE OR REPLACE FUNCTION refresh_instances()
|
||||||
|
RETURNS trigger AS $$
|
||||||
|
BEGIN
|
||||||
|
REFRESH MATERIALIZED VIEW instances;
|
||||||
|
RETURN NULL;
|
||||||
|
END;
|
||||||
|
$$ LANGUAGE plpgsql;
|
||||||
|
"""
|
||||||
|
end
|
||||||
|
|
||||||
|
def drop_trigger do
|
||||||
|
"""
|
||||||
|
DROP TRIGGER IF EXISTS refresh_instances_trigger ON actors;
|
||||||
|
"""
|
||||||
|
end
|
||||||
|
|
||||||
|
def create_trigger do
|
||||||
|
"""
|
||||||
|
CREATE TRIGGER refresh_instances_trigger
|
||||||
|
AFTER INSERT OR UPDATE OR DELETE
|
||||||
|
ON actors
|
||||||
|
FOR EACH STATEMENT
|
||||||
|
EXECUTE PROCEDURE refresh_instances();
|
||||||
|
"""
|
||||||
|
end
|
||||||
|
|
||||||
|
def drop_refresh_instances do
|
||||||
|
"""
|
||||||
|
DROP FUNCTION IF EXISTS refresh_instances() CASCADE;
|
||||||
|
"""
|
||||||
|
end
|
||||||
|
|
||||||
|
def drop_view do
|
||||||
|
"""
|
||||||
|
DROP MATERIALIZED VIEW IF EXISTS instances;
|
||||||
|
"""
|
||||||
|
end
|
||||||
|
end
|
|
@ -1,51 +1,15 @@
|
||||||
defmodule Mobilizon.Storage.Repo.Migrations.AddInstanceMaterializedView do
|
defmodule Mobilizon.Storage.Repo.Migrations.AddInstanceMaterializedView do
|
||||||
use Ecto.Migration
|
use Ecto.Migration
|
||||||
|
alias Mobilizon.Storage.Views.Instances
|
||||||
|
|
||||||
def up do
|
def up do
|
||||||
execute("""
|
execute(Instances.create_materialized_view())
|
||||||
CREATE MATERIALIZED VIEW instances AS
|
|
||||||
SELECT
|
|
||||||
a.domain,
|
|
||||||
COUNT(DISTINCT(p.id)) AS person_count,
|
|
||||||
COUNT(DISTINCT(g.id)) AS group_count,
|
|
||||||
COUNT(DISTINCT(e.id)) AS event_count,
|
|
||||||
COUNT(f1.id) AS followers_count,
|
|
||||||
COUNT(f2.id) AS followings_count,
|
|
||||||
COUNT(r.id) AS reports_count,
|
|
||||||
SUM(COALESCE((m.file->>'size')::int, 0)) AS media_size
|
|
||||||
FROM actors a
|
|
||||||
LEFT JOIN actors p ON a.id = p.id AND p.type = 'Person'
|
|
||||||
LEFT JOIN actors g ON a.id = g.id AND g.type = 'Group'
|
|
||||||
LEFT JOIN events e ON a.id = e.organizer_actor_id
|
|
||||||
LEFT JOIN followers f1 ON a.id = f1.actor_id
|
|
||||||
LEFT JOIN followers f2 ON a.id = f2.target_actor_id
|
|
||||||
LEFT JOIN reports r ON r.reported_id = a.id
|
|
||||||
LEFT JOIN medias m ON m.actor_id = a.id
|
|
||||||
WHERE a.domain IS NOT NULL
|
|
||||||
GROUP BY a.domain;
|
|
||||||
""")
|
|
||||||
|
|
||||||
execute("""
|
execute(Instances.refresh_instances())
|
||||||
CREATE OR REPLACE FUNCTION refresh_instances()
|
|
||||||
RETURNS trigger AS $$
|
|
||||||
BEGIN
|
|
||||||
REFRESH MATERIALIZED VIEW instances;
|
|
||||||
RETURN NULL;
|
|
||||||
END;
|
|
||||||
$$ LANGUAGE plpgsql;
|
|
||||||
""")
|
|
||||||
|
|
||||||
execute("""
|
execute(Instances.drop_trigger())
|
||||||
DROP TRIGGER IF EXISTS refresh_instances_trigger ON actors;
|
|
||||||
""")
|
|
||||||
|
|
||||||
execute("""
|
execute(Instances.create_trigger())
|
||||||
CREATE TRIGGER refresh_instances_trigger
|
|
||||||
AFTER INSERT OR UPDATE OR DELETE
|
|
||||||
ON actors
|
|
||||||
FOR EACH STATEMENT
|
|
||||||
EXECUTE PROCEDURE refresh_instances();
|
|
||||||
""")
|
|
||||||
|
|
||||||
create_if_not_exists(unique_index("instances", [:domain]))
|
create_if_not_exists(unique_index("instances", [:domain]))
|
||||||
end
|
end
|
||||||
|
@ -53,12 +17,8 @@ defmodule Mobilizon.Storage.Repo.Migrations.AddInstanceMaterializedView do
|
||||||
def down do
|
def down do
|
||||||
drop_if_exists(unique_index("instances", [:domain]))
|
drop_if_exists(unique_index("instances", [:domain]))
|
||||||
|
|
||||||
execute("""
|
execute(Instances.drop_refresh_instances())
|
||||||
DROP FUNCTION IF EXISTS refresh_instances() CASCADE;
|
|
||||||
""")
|
|
||||||
|
|
||||||
execute("""
|
execute(Instances.drop_view())
|
||||||
DROP MATERIALIZED VIEW IF EXISTS instances;
|
|
||||||
""")
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -0,0 +1,48 @@
|
||||||
|
defmodule Mobilizon.Storage.Repo.Migrations.RemoveOnDeleteCascadeForReports do
|
||||||
|
use Ecto.Migration
|
||||||
|
alias Mobilizon.Storage.Views.Instances
|
||||||
|
|
||||||
|
def up do
|
||||||
|
execute(Instances.drop_view())
|
||||||
|
|
||||||
|
drop(constraint(:reports, "reports_reported_id_fkey"))
|
||||||
|
drop(constraint(:reports, "reports_reporter_id_fkey"))
|
||||||
|
drop(constraint(:reports, "reports_manager_id_fkey"))
|
||||||
|
|
||||||
|
alter table(:reports) do
|
||||||
|
modify(:reported_id, references(:actors, on_delete: :nilify_all), null: true)
|
||||||
|
modify(:reporter_id, references(:actors, on_delete: :nilify_all), null: true)
|
||||||
|
modify(:manager_id, references(:actors, on_delete: :nilify_all), null: true)
|
||||||
|
end
|
||||||
|
|
||||||
|
drop(constraint(:report_notes, "report_notes_moderator_id_fkey"))
|
||||||
|
|
||||||
|
alter table(:report_notes) do
|
||||||
|
modify(:moderator_id, references(:actors, on_delete: :nilify_all), null: true)
|
||||||
|
end
|
||||||
|
|
||||||
|
execute(Instances.create_materialized_view())
|
||||||
|
end
|
||||||
|
|
||||||
|
def down do
|
||||||
|
execute(Instances.drop_view())
|
||||||
|
|
||||||
|
drop(constraint(:reports, "reports_reported_id_fkey"))
|
||||||
|
drop(constraint(:reports, "reports_reporter_id_fkey"))
|
||||||
|
drop(constraint(:reports, "reports_manager_id_fkey"))
|
||||||
|
|
||||||
|
alter table(:reports) do
|
||||||
|
modify(:reported_id, references(:actors, on_delete: :delete_all), null: false)
|
||||||
|
modify(:reporter_id, references(:actors, on_delete: :delete_all), null: false)
|
||||||
|
modify(:manager_id, references(:actors, on_delete: :delete_all), null: true)
|
||||||
|
end
|
||||||
|
|
||||||
|
drop(constraint(:report_notes, "report_notes_moderator_id_fkey"))
|
||||||
|
|
||||||
|
alter table(:report_notes) do
|
||||||
|
modify(:moderator_id, references(:actors, on_delete: :delete_all), null: false)
|
||||||
|
end
|
||||||
|
|
||||||
|
execute(Instances.create_materialized_view())
|
||||||
|
end
|
||||||
|
end
|
Loading…
Reference in a new issue