From bab8fc2d2922e1040a77be632168ed5aedaa0f6a Mon Sep 17 00:00:00 2001 From: mfo Date: Tue, 27 Aug 2024 11:01:28 +0200 Subject: [PATCH] fix(delete_orphaned_champs): maintenance tasks with custom PG_STATEMENT_TIMEOUT is not a good fit. change implementation to after_party --- ...phaned_champs_with_missing_dossier_task.rb | 33 ------------- ..._orphaned_champs_with_missing_dossier.rake | 18 +++++++ ...d_champs_with_missing_dossier_task_spec.rb | 47 ------------------- 3 files changed, 18 insertions(+), 80 deletions(-) delete mode 100644 app/tasks/maintenance/delete_orphaned_champs_with_missing_dossier_task.rb create mode 100644 lib/tasks/deployment/20240827085815_delete_orphaned_champs_with_missing_dossier.rake delete mode 100644 spec/tasks/maintenance/delete_orphaned_champs_with_missing_dossier_task_spec.rb diff --git a/app/tasks/maintenance/delete_orphaned_champs_with_missing_dossier_task.rb b/app/tasks/maintenance/delete_orphaned_champs_with_missing_dossier_task.rb deleted file mode 100644 index 533eb25df8f..00000000000 --- a/app/tasks/maintenance/delete_orphaned_champs_with_missing_dossier_task.rb +++ /dev/null @@ -1,33 +0,0 @@ -# frozen_string_literal: true - -module Maintenance - # On our production environment, the fk between `champs.dossier_id` and `dossiers.id` had not been created - # this maintenance task cleans up orphaned champ pointing to deleted dossier - # next step is to validate the recreated fk - # For our own record, use it with PG_STATEMENT_TIMEOUT=300000 .... - class DeleteOrphanedChampsWithMissingDossierTask < MaintenanceTasks::Task - def collection - Champ.select(:id, :type).where.missing(:dossier) - end - - def process(champ) - champ.reload # in case we need more data on this champ - - case champ.type - when 'Champs::CarteChamp' then - champ.geo_areas.delete_all - when 'Champs::RepetitionChamp' then - champ.champs.delete_all - when 'Champs::SiretChamp' then - etablissement = champ.etablissement - champ.update(etablissement_id: nil) - etablissement.delete - end - champ.delete - end - - def count - # no count, it otherwise it will timeout - end - end -end diff --git a/lib/tasks/deployment/20240827085815_delete_orphaned_champs_with_missing_dossier.rake b/lib/tasks/deployment/20240827085815_delete_orphaned_champs_with_missing_dossier.rake new file mode 100644 index 00000000000..890d1ae72ff --- /dev/null +++ b/lib/tasks/deployment/20240827085815_delete_orphaned_champs_with_missing_dossier.rake @@ -0,0 +1,18 @@ +# frozen_string_literal: true + +namespace :after_party do + desc 'Deployment task: delete_orphaned_champs_with_missing_dossier' + task delete_orphaned_champs_with_missing_dossier: :environment do + puts "Running deploy task 'delete_orphaned_champs_with_missing_dossier'" + + Champ.select(:id, :type).where.missing(:dossier).each do |champ| + champ.champs.destroy_all if champ.type == 'Champs::RepetitionChamp' + champ.destroy + end + + # Update task as completed. If you remove the line below, the task will + # run with every deploy (or every time you call after_party:run). + AfterParty::TaskRecord + .create version: AfterParty::TaskRecorder.new(__FILE__).timestamp + end +end diff --git a/spec/tasks/maintenance/delete_orphaned_champs_with_missing_dossier_task_spec.rb b/spec/tasks/maintenance/delete_orphaned_champs_with_missing_dossier_task_spec.rb deleted file mode 100644 index 60a171e742f..00000000000 --- a/spec/tasks/maintenance/delete_orphaned_champs_with_missing_dossier_task_spec.rb +++ /dev/null @@ -1,47 +0,0 @@ -# frozen_string_literal: true - -require "rails_helper" - -module Maintenance - RSpec.describe DeleteOrphanedChampsWithMissingDossierTask do - describe "#process" do - let(:procedure) { create(:procedure, types_de_champ_public:) } - let(:dossier) { create(:dossier, :with_populated_champs, procedure:) } - let(:champ) { dossier.champs.first } - - subject(:process) { described_class.process(champ) } - - context 'with other champs' do - let(:types_de_champ_public) { [{ type: :text }] } - it 'delete champ' do - expect { subject }.to change { Champ.exists?(champ.id) }.from(true).to(false) - end - end - - context "with carte" do - let(:types_de_champ_public) { [{ type: :carte }] } - it 'deletes champ.geo_areas' do - geo_area_ids = champ.geo_areas.ids - expect { subject }.to change { GeoArea.where(id: geo_area_ids).count }.from(2).to(0) - expect(Champ.exists?(champ.id)).to be_falsey - end - end - - context "with repetition" do - let(:types_de_champ_public) { [{ type: :repetition, mandatory: true, children: [{ type: :text }] }] } - it 'deletes champ.champs (children)' do - expect { subject }.to change { champ.champs.count }.from(2).to(0) - expect(Champ.exists?(champ.id)).to be_falsey - end - end - - context "with siret" do - let(:types_de_champ_public) { [{ type: :siret }] } - it 'delete champ.etablissement' do - expect { subject }.to change { Etablissement.exists?(champ.etablissement_id) }.from(true).to(false) - expect(Champ.exists?(champ.id)).to be_falsey - end - end - end - end -end