The SoftDelete Annotation

Built-in Soft Delete (Hibernate 6.4+)

Hibernate 6.4 added @SoftDelete. It writes both the UPDATE and the restriction for you, and also works on collections.

import org.hibernate.annotations.SoftDelete;
import org.hibernate.annotations.SoftDeleteType;

@Entity
@Table(name = "cart_items")
@SoftDelete                                          // boolean column "deleted"
public class CartItem { ... }

@Entity
@Table(name = "users")
@SoftDelete(columnName = "active", strategy = SoftDeleteType.ACTIVE)   // active = true means visible
public class User { ... }

SQL Log

cartItemRepository.delete(item);

Example output

update cart_items set deleted=true where id=? and deleted=false

Choosing

@SQLDelete + @SQLRestriction@SoftDelete
Hibernate versionany 6.x (6.3+ for @SQLRestriction)6.4+
Columnanything you like (flag, timestamp, status)boolean-style indicator column
Extra data on deleteyes: set deleted_at = now(), deleted_by = ... in the SQLno
Effortwrite SQL per entityone annotation

Tip: If you need deleted_at and deleted_by for audits, stay with @SQLDelete, or record them in an audit table with Hibernate Envers.