Often times, applications cannot get rid of the database records for business rules. For example, if you are a cable TV provider, you might have a customer calling you to stop the National Geographic Channel subscription from next month. Ideally you would like to delete this record, but you can't do it until the effective date:( If you delete it, the next invoice will not be able to charge for this channel, although it's still being used.
In such scenarios, its common to fall back to a soft delete model. As an example, here's a little code:
This code looks simple and harmless at a first sight. But, as you develop your app, you'll run into a lot of issues from this. Here's a short list:
In such scenarios, its common to fall back to a soft delete model. As an example, here's a little code:
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#example code to cancel subscription | |
Customer.find('John Fake').tv_channel_subscriptions.find(:nat_geo).cancel!(1.month.from_now) | |
class Customer | |
attr_accessor :name, :start_date, :end_date | |
has_many :tv_channel_subscriptions | |
end | |
class TvChannelSubscription | |
attr_accessor :monthly_fee, :start_date, :end_date | |
belongs_to :customer | |
belongs_to :tv_channel | |
def cancel!(effective_date) | |
end_date = effective_date | |
save! | |
end | |
end | |
class TvChannel | |
attr_accessor :name | |
end |
This code looks simple and harmless at a first sight. But, as you develop your app, you'll run into a lot of issues from this. Here's a short list:
- You need to take care of cascading soft delete, for example, cancelling a customer's subscription needs to cascade down to all channels and other objects under it.
- Whenever, you are listing the current subscriptions of a customer, you need to filter out the ended ones.
- You need to figure out a strategy to periodically clean the ended subscriptions so that your database is not filled with outdated data.
- If you have a business key used as a primary key as well, you will be in trouble if an ended subscription is restarted.
- Your code will eventually have a lot of if-else blocks to apply changes to only on active objects.