The main problem I have is the article takes a performance/devlopment lens to soft deletes, and only pays lip service to the objectives you're trading off performance for with soft deletes ... namely data retention / disaster recovery / audit requirements. * availability / recovery - soft deletes provide the best RPO/RTO in archival / lifecycle planning * auditability / compliance - much easier to achieve with 1 syst…
Avoiding the soft delete anti-pattern
21–30 of 61 posts
Re: Avoiding the soft delete anti-pattern
#22How about a separate, schema-wise identical "deleted_x" table that you "move" deleted entities to? Can't get much more explicit than that, and still enables whatever joins you'd like on historical deleted data.
But I'd usually consider soft delete alongside this approach, as it always really depends on what you're doing and what your needs are - if you constantly query the dependent records joined to the entity you may or may not delete, then a deleted entity table means you now need to left join two tables when before you could inner join one table. So soft delete might be simpler.
But if that's a rare use case, then soft delete might be more complex depending on how many separate codepaths are querying the primary entity.
My next blog post should be called "It depends - avoiding the overly broad generalisations anti-pattern".
Re: Avoiding the soft delete anti-pattern
#23So we call approaches 'anti-patterns' now if they aren't universally suitable?
Re: Avoiding the soft delete anti-pattern
#24“Soft-Delete pattern (deleted_at column) or any other pattern adding $event_at column to a DB table, contains an ad hoc, informally-specified, bug-ridden, slow implementation of half of Event Sourcing.” — Greenspun's tenth rule of programming
Seriously, event sourcing is hard to do right, maybe soft delete is the simpler approach, it depends on what you're doing.
Re: Avoiding the soft delete anti-pattern
#25“Soft-Delete pattern (deleted_at column) or any other pattern adding $event_at column to a DB table, contains an ad hoc, informally-specified, bug-ridden, slow implementation of half of Event Sourcing.” — Greenspun's tenth rule of programming
As opposed to event sourcing, which every time I've seen it in use, contains a bug ridden slow implementation of event sourcing. Seriously, event sourcing is hard to do right, maybe soft delete is the simpler approach, it depends on what you're doing.
IMO, if entity might be resurrected/revived/“undeleted”, then it either cannot be killed/deleted, or more likely what you thought as “deletion” was something else (e.g. suspending, archiving, hiding, or putting into trash bin).
It’s better to model a lifecycle of such an entity as an FSM.
And yes, Event Sourcing might be harder in some respects, but it’s make things easier in others, as it makes soft-delete and tens of other design patterns redundant.
Re: Avoiding the soft delete anti-pattern
#26Earlier quoted context omitted.
As opposed to event sourcing, which every time I've seen it in use, contains a bug ridden slow implementation of event sourcing. Seriously, event sourcing is hard to do right, maybe soft delete is the simpler approach, it depends on what you're doing.
The problem is that people’s first choice is to use generic models like CRUD/CRUD-L/REST/etc., instead of unvesting a bit of time in upfront thinking/design and building a custom model. IMO, if entity might be resurrected/revived/“undeleted”, then it either cannot be killed/deleted, or more likely what you thought as “deletion” was something else (e.g. suspending, archiving, hiding, or putting into trash bin). It’s b…
Re: Avoiding the soft delete anti-pattern
#27Earlier quoted context omitted.
The problem is that people’s first choice is to use generic models like CRUD/CRUD-L/REST/etc., instead of unvesting a bit of time in upfront thinking/design and building a custom model. IMO, if entity might be resurrected/revived/“undeleted”, then it either cannot be killed/deleted, or more likely what you thought as “deletion” was something else (e.g. suspending, archiving, hiding, or putting into trash bin). It’s b…
I've never seen it done well, and yeah, it sounds good in theory, in reality, blurgh.
IMO, this is b/c it takes years to learn and apply, on top of already having significant CRUD experience
Corporate drones are not incentivized to do this, and startup people are pressed with time
So it may only work if there are highly motivated people, who may peridically ask for help from expirienced consultants, but not fully rely on them.
So do it this way:
> It’s better to model a lifecycle of such an entity as an FSM
Re: Avoiding the soft delete anti-pattern
#28Re: Avoiding the soft delete anti-pattern
#29Soft delete is the only way to make this possible without horrible kludges.
Re: Avoiding the soft delete anti-pattern
#30Earlier quoted context omitted.
If the thing you want to do with the deleted data is mostly ad-hoc support queries (that is you are keeping the current workflow, not adding new UI and functionality for pervasive restores) then I feel like moving deleted entries to a new "shadow table" with the same schema (eg subscription might have a soft_deleted_subscription shadow) might work well for you. I have never implemented this, but I feel like it would…
That is a possibility. But all our "soft-delete targets" have at least 2-3 levels of child tables, it's never just one table. So that complicates matters. For example, it could be the user deletes a customer entry in our system, the customer has contacts, and each contact has multiple contact methods say. There are many other child tables for a customer, like delivery addresses and official id numbers and so on, this…