From f4902421eaa50dea98dc5046848f95c959cb3c88 Mon Sep 17 00:00:00 2001 From: Benjamin Neff Date: Thu, 12 Oct 2017 02:43:37 +0200 Subject: [PATCH] Destroy user and person associations in batches --- lib/account_deleter.rb | 21 ++++++++++++--------- spec/lib/account_deleter_spec.rb | 18 +++++++++++++----- 2 files changed, 25 insertions(+), 14 deletions(-) diff --git a/lib/account_deleter.rb b/lib/account_deleter.rb index b14582980..356c5a54c 100644 --- a/lib/account_deleter.rb +++ b/lib/account_deleter.rb @@ -5,7 +5,6 @@ # the COPYRIGHT file. class AccountDeleter - # Things that are not removed from the database: # - Comments # - Likes @@ -44,7 +43,7 @@ class AccountDeleter tombstone_user end - #user deletions + # user deletions def normal_ar_user_associates_to_delete %i[tag_followings services aspects user_preferences notifications blocks authorizations o_auth_applications pairwise_pseudonymous_identifiers] @@ -61,13 +60,17 @@ class AccountDeleter def delete_standard_user_associations normal_ar_user_associates_to_delete.each do |asso| - self.user.send(asso).each{|model| model.destroy } + user.send(asso).ids.each_slice(20) do |ids| + User.reflect_on_association(asso).class_name.constantize.where(id: ids).destroy_all + end end end def delete_standard_person_associations normal_ar_person_associates_to_delete.each do |asso| - self.person.send(asso).destroy_all + person.send(asso).ids.each_slice(20) do |ids| + Person.reflect_on_association(asso).class_name.constantize.where(id: ids).destroy_all + end end end @@ -78,7 +81,7 @@ class AccountDeleter # Currently this would get deleted due to the db foreign key constrainsts, # but we'll keep this method here for completeness def remove_share_visibilities_on_contacts_posts - ShareVisibility.for_a_user(user).destroy_all + ShareVisibility.for_a_user(user).find_each(batch_size: 20, &:destroy) end def remove_conversation_visibilities @@ -86,16 +89,16 @@ class AccountDeleter end def tombstone_person_and_profile - self.person.lock_access! - self.person.clear_profile! + person.lock_access! + person.clear_profile! end def tombstone_user - self.user.clear_account! + user.clear_account! end def delete_contacts_of_me - Contact.all_contacts_of_person(self.person).destroy_all + Contact.all_contacts_of_person(person).find_each(batch_size: 20, &:destroy) end def normal_ar_person_associates_to_delete diff --git a/spec/lib/account_deleter_spec.rb b/spec/lib/account_deleter_spec.rb index a82bbe578..a6445a3b9 100644 --- a/spec/lib/account_deleter_spec.rb +++ b/spec/lib/account_deleter_spec.rb @@ -96,8 +96,12 @@ describe AccountDeleter do it 'removes all standard user associaltions' do @account_deletion.normal_ar_user_associates_to_delete.each do |asso| association_double = double - expect(association_double).to receive(:destroy) - expect(bob).to receive(asso).and_return([association_double]) + expect(association_double).to receive(:ids).and_return([42]) + expect(bob).to receive(asso).and_return(association_double) + batch_double = double + expect(User.reflect_on_association(asso).class_name.constantize).to receive(:where) + .with(id: [42]).and_return(batch_double) + expect(batch_double).to receive(:destroy_all) end @account_deletion.delete_standard_user_associations @@ -111,8 +115,12 @@ describe AccountDeleter do it 'removes all standard person associaltions' do @account_deletion.normal_ar_person_associates_to_delete.each do |asso| association_double = double - expect(association_double).to receive(:destroy_all) + expect(association_double).to receive(:ids).and_return([42]) expect(bob.person).to receive(asso).and_return(association_double) + batch_double = double + expect(Person.reflect_on_association(asso).class_name.constantize).to receive(:where) + .with(id: [42]).and_return(batch_double) + expect(batch_double).to receive(:destroy_all) end @account_deletion.delete_standard_person_associations @@ -133,7 +141,7 @@ describe AccountDeleter do it 'deletes all the local contact objects where deleted account is the person' do contacts = double expect(Contact).to receive(:all_contacts_of_person).with(bob.person).and_return(contacts) - expect(contacts).to receive(:destroy_all) + expect(contacts).to receive(:find_each).with(batch_size: 20) @account_deletion.delete_contacts_of_me end end @@ -163,7 +171,7 @@ describe AccountDeleter do it "removes the share visibilities for a user" do s_vis = double expect(ShareVisibility).to receive(:for_a_user).with(bob).and_return(s_vis) - expect(s_vis).to receive(:destroy_all) + expect(s_vis).to receive(:find_each).with(batch_size: 20) @account_deletion.remove_share_visibilities_on_contacts_posts end