# 逻辑删除时唯一索引解决方案

# 1.概述

在数据库表中,如果使用了逻辑删除,则会出现无法创建唯一索引的问题,导致在高并发环境下创建的数据会出现重复情况,引起业务异常;为了解决无法创建唯一索引增加虚拟列配置功能。

# 2.虚拟列使用

# 虚拟列注解

@Inherited
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.FIELD})
public @interface Unreal {

    /**
     * TODO 用与新增和修改时填充,这里维护的是实体字段,默认值是code,多个字段用逗号分割
     * @author whh
     * @date 2025-03-27 上午11:23
     */
    String fillInsertOrUpdate() default "code";

    /**
     * TODO 用于填充删除时赋值,这里维护的是表字段,默认值是id,多个字段用逗号分割
     * @author whh
     * @date 2025-03-31 下午6:26
     */
    String fillDelete() default "id";

}

fillInsertOrUpdate: 用于新增和修改时填充虚拟列,这里维护的是实体字段,默认值是code,多个字段用逗号分割。


fillDelete: 用于逻辑删除时填充虚拟列,这里维护的是表字段,默认值是id,多个字段用逗号分割。

# 实体类

为了方便管理,提升代码速度,虚拟列统一命名为unreal

public class demo{
    @ApiModelProperty(value = "虚拟的列无实际意义,主要是用于唯一索引使用")
    @TableField(value = "unreal",fill= FieldFill.INSERT_UPDATE)
    @Unreal
    private String unreal;
    
}

# 配置类说明

由于使用了mybatisplus自动填充功能,因此使用自动填充类时需要继承AbstractMetaObjectHandler;并且在自定义配置MybatisPlusInterceptor类时添加HosVirtualInterceptor拦截器到配置容器中。