Skip to content

How to: Soft delete a user when user deletes account

Morris Kimani edited this page Jul 30, 2019 · 10 revisions

Delete User Account but Retain User Data (Soft Delete)

When a user chooses to delete their account, all of their data is destroyed by devise. It may be advantageous to keep the user data but make the user inactive and unable to log in.

This is how you can soft delete a user:

  1. Add a "deleted_at" DATETIME column
  2. Override users/registrations#destroy in your routes
  3. Override users/registrations#destroy in the registrations controller
  4. Update user model with a soft_delete & check if user is active on authentication
  5. Add a custom delete message

1. Add deleted_at column to Users

  • rails g migration AddDeletedAtColumnToUsers deleted_at:datetime
  • rake db:migrate

2. Override the delete route in config/routes.rb

devise_for :users, :controllers => { :registrations => 'users/registrations' }

3. Override users/registrations#destroy in registrations controller

  • Create app/controllers/users/registrations_controller.rb if it does not already exist
    • Extend the Devise registrations controller
    • Override the destroy method
# app/controllers/users/registrations_controller.rb
class Users::RegistrationsController < Devise::RegistrationsController
  # DELETE /resource
  def destroy
    resource.soft_delete
    Devise.sign_out_all_scopes ? sign_out : sign_out(resource_name)
    set_flash_message :notice, :destroyed
    yield resource if block_given?
    respond_with_navigational(resource){ redirect_to after_sign_out_path_for(resource_name) }
  end
end

4. Update the user model with soft_delete method & check if user is active when authenticating

  # app/models/user.rb  
  
  # instead of deleting, indicate the user requested a delete & timestamp it  
  def soft_delete  
    update_attribute(:deleted_at, Time.current)  
  end  
  
  # ensure user account is active  
  def active_for_authentication?  
    super && !deleted_at  
  end  
  
  # provide a custom message for a deleted account   
  def inactive_message   
    !deleted_at ? super : :deleted_account  
  end  

5. Add custom error message when trying to login with a deleted account.

# config/locales/*your-filename-here*.yml
en:  
  devise:  
    failure:  
      deleted_account: "You've deleted your account. Thanks!"  
Clone this wiki locally