136

软删除是好主意还是坏主意?

无需实际删除数据库中的记录,您只需将其标记为IsDeleted = true,并且在恢复记录后,您可以将其标记为False

这是一个好主意吗?

物理删除记录,然后将其移动到存档数据库,如果用户想要恢复记录,那么软件将在存档中查找记录并重新创建它是不是更好?

4

15 回答 15

100

I say it's a bad idea, generally (with some exceptions, perhaps).

First, your database should be backed up regularly, so you should never be in a situation where you would lose data permanently because of a DELETE (unless it's a deletion of just-added data, of course).

Second, a soft delete like this means you now have to include a WHERE IsDeleted = false clause in every query on this table (and so much worse if you're JOINing these tables). A mistake here would be caught as soon as a user or tester noticed a deleted record showing up again, which might take some time. Also, it would be easy for a developer to omit the WHERE clause from COUNT(*) queries, which might take even longer to discover (I worked on one project where this had been happening for years; not many records were ever "deleted", so the totals were close to what was expected and no one noticed).

Finally, a soft delete will work on a table with artificial keys, but potentially won't work on a table with a natural primary key (e.g. you "delete" someone from a table keyed by Social Security Number - what do you do when you need to add him back? Please don't say "include IsDeleted in a compound primary key".).

In a design review, I would expect the developer to demonstrate an awareness of the costs and benefits and to present an excellent reason for doing soft deletes in this manner. "Why not do it?" is not an excellent reason.

于 2010-03-31T01:51:56.180 回答
93

避免潜在的数据丢失绝不是一个坏主意。

我总是软删除。在需要清除数据库中的一条或多条记录的情况下,我通常采用软删除的两步过程,然后清空记录的“回收站”,或者采用文档管理风格的方法,其中文档记录可以被老化,然后在硬删除之前通过审批流程。

于 2010-03-31T01:24:04.243 回答
32

It depends on the circumstances. I could see situations where you are legally required to truly delete something. Maybe someone has requested that their social security number be permanently removed from your system. Or maybe you have a duplicate record that you want to consolidate into a single record. Keeping the duplicate hanging around with a deleted flag might not be advantageous.

There is also one technical disadvantage: You can't do cascading deletions, which automatically clear out any references to the deleted data to prevent foreign key violations. This isn't necessarily a big issue, but it's something to keep in mind.

Otherwise, I think it's a good idea.

于 2010-03-31T01:29:25.603 回答
24

如果要使用软删除,最好使用 deleted_date 字段,而不是 is_deleted 字段。你会得到一个很好的额外数据,而不仅仅是位字段。

于 2010-04-01T13:02:23.583 回答
20

One of the major problem for soft delete is those unwanted data will potentially affects the db performance. Several years ago one of my Client requested me to do soft delete on all database items, my solution to that is to move all "deleted" items to a backup table, instead of leaving it to the current running tables.

于 2010-03-31T01:31:39.660 回答
17

如果无效删除绝对是灾难性的,并且恢复应该很简单,这是一个好主意。如果您想跟踪曾经存在的所有内容,并且“删除”实际上仅意味着“隐藏”,这也是一个好主意。意思是,视情况而定。

于 2010-03-31T01:25:06.943 回答
9

我不会试图“在政治上正确”。如果您提倡软删除,那么您需要进行大脑检查。

1)首先,通过不删除表中的行,您究竟实现了什么?只是事实是将来某个时候您可以访问这些行,对吗?那么为什么不直接创建一个存档表并将行移到那里呢?那有什么问题?

2) 使用软删除,您将在 is_active 上创建不必要的查询或在某些时间戳列上进行查询。当您编写更简单的查询时,这只是浪费。是的,它可以与视图一起使用,但视图不是额外的附属物吗?每个视图都是一个额外的 SQL,额外的性能成本,在任何商业 RDBMS 中,一切都只是一个表。除了您不知道如何在表之上编写查询这一事实之外,视图并没有什么神奇之处。

3) 是的,它将与视图或 MV 一起使用。但是后来我看到生产中的查询在做 FTS 并且一切仍然有效!现代硬件和可靠软件的奇迹。但这也不是正确的。所以按照同样的逻辑,仅仅因为它有效并不意味着它是正确的

4) 软删除的复杂性永远不会停留在简单的选择上。

A)假设您有一个 UNIQUE 约束。现在您软删除了一行,但具有 UNIQUE 约束的列仍然存在。当您想重新添加相同的数据时,如果没有额外的“技巧”,您将无法做到这一点。

B)您可能有从表 A 到表 B 的关联,并且当您从表 A 中软删除某些内容时,您需要确保表 B 上的独立查询处理该事实。假设一个典型的详细信息页面正在处理某个 detail_id。

现在,master_id 被软删除,但您仍然在任何地方都有带有该 master_id 的 detail_id 的永久链接。当您对 master_id 进行硬删除时,这些详细信息根本不存在。现在,通过软删除,它们仍然存在,并且它们必须知道它们的 master_id 处于软删除模式这一事实。

它不会停留在简单的 Table_A.is_active = 0 或 1 阶段。

5) 进行硬删除既简单又正确。

A)没有人需要在任何地方添加任何额外的东西或担心任何事情。

  1. 您的应用程序逻辑更简单
  2. 您的数据库较小
  3. 您的查询速度更快

只需归档数据+相关部分,你应该会很好。

于 2012-03-05T10:04:56.207 回答
8

Soft deletes would also allow you to revoke DELETE privileges from the database account used by the application.

于 2010-03-31T01:27:47.687 回答
5

有时软删除是必要的。例如,假设您有一个引用 Products 表的 Invoice 表。一旦您使用特定产品创建了发票,您就永远无法删除该产品(如果您的 RI 设置正确,它不会让您删除)。

此特定场景假定您永远不想删除发票,而在真实公司中您可能不想删除历史财务数据。

尽管在许多其他情况下,您将无法删除某些数据,这是由于业务或其他原因无法删除链上依赖关系的副作用。

于 2010-03-31T01:36:25.777 回答
4

这取决于数据。由于法律/审计要求,某些数据无法删除。

另一方面,社交网站应该提供一个选项来删除一个包含所有相关数据的帐户,包括联系信息、照片、消息等。如果他们不这样做,这将是一个真正的烦恼,例如 Facebook。

于 2010-03-31T01:33:01.977 回答
4

在oracle中,如果您将主键添加到您组成的recycle_bin表中,然后添加行级安全策略,您可以在行在回收站中时抑制所有查询的值,从回收站中删除pk会自动恢复所有数据。无需更改其他查询以适应逻辑。

于 2010-04-23T01:53:16.080 回答
3

It comes with a cost, though, because you need to update your queries and indexes to be able to exclude the deleted rows.

Maybe instead of toggling a flag, move it to another "trash can" table.

Also, one could say that is only a partial solution, because it covers only deletes, but when you update a row, you are still overwriting the old value.

In general, I'd say never delete anything unless you really have to. Disk space is cheap these days. Of course, there are limits, there is data that you are legally bound to erase, there is data that is really not all that important, and maybe you do not need to keep the old data online and in the same table (an archive somewhere would also work).

于 2010-03-31T01:30:12.957 回答
1

只是为了增加一分钱。我总是软删除;虽然它确实花费了性能,但非常轻微。考虑一下成本,当您的客户抱怨您的软件在她执行某些甚至她不记得的操作后停止运行时。好吧,这可能是一个胖例子,但你永远不会知道出了什么问题,谁做了什么,之前是什么,之后插入了什么。在这种情况下,这将派上用场。此功能可用于审计目的,许多客户要求审计此类报告。

此外,在大多数基于工作流的应用程序中,客户对在工作项上执行的“操作”感兴趣的软件功能/要求;分配了哪些值以及谁处理了它等。

于 2010-03-31T05:54:47.707 回答
0

我是软删除的粉丝。主要是为了防止级联删除。但是,它需要额外的代码,因此如果您正在选择一个子对象,它会连接到父对象(以及所有父对象!)以确保它们都不会被删除。或者,您可以级联软删除,但如果您想稍后恢复它们,您可能不知道哪些子级已被删除,哪些因级联而被删除。

此外,我在每个对象上保留了修订日期时间和修订用户名,以便我知道谁最后修改(或软删除)它。然后,对于审计跟踪,我创建了一个 *History(如 CustomerHistory)表,该表在每次 UPDATE 后插入到原始表中。这样,在修改或软删除对象后,我可以记录谁执行了该操作以及该对象的最后已知状态。

于 2010-03-31T02:40:42.567 回答
0

我遇到了以下广泛场景的软删除:

案例1:从用户/代码可见中删除记录,但在数据库级别保留记录,因为企业有兴趣知道它有这些记录。
这些要求主要由业务驱动,通常核心可能是法律要求(如@joshperry 和@armandino 场景),在数据库中拥有先前的记录并为每次更改创建新记录。在这一点上,我会查看 CASE 2 并评估它是否满足要求,然后再设置 IsDeleted 标志

案例 2:跟踪记录演变的审计跟踪 - 网上有大量不错的文章可用于在数据库中保存记录的审计跟踪

HTH。

于 2010-03-31T02:41:52.543 回答