主键生成策略解读(@TableId)

2024-05-09 08:59:36 浏览数 (2)

基本介绍

主键的作用是唯一标识,我们可以通过这个唯一标识来定位到这条数据。在数据库表数据中,主键的生成可以遵循自定义的规则,但手动生成通常比较繁琐。因此,在实际开发中,我们更倾向于使用框架提供的主键生成策略来自动生成主键。

在MybatisPlus中,提供了@TableId注解来指定主键生成策略。这个注解允许我们为新增的数据指定主键生成方式。

@TableId 注解属性

属性

类型

必须指定

默认值

描述

value

String

""

主键字段名

type

Enum

IdType.NONE

指定主键类型

type 类型枚举

  • AUTO:数据库ID自增。该策略跟随数据库表的主键递增策略,前提是数据库表的主键要设置为自增。
  • NONE:无状态,该类型为未设置主键类型(注解里等于跟随全局,全局里约等于INPUT)。
  • INPUT:insert前自行set主键值。如果未设置主键值,则无法添加数据。
  • ASSIGN_ID:分配ID(主键类型为Number(Long和Integer)或String)。使用接口IdentifierGenerator的方法nextId(默认实现类为DefaultIdentifierGenerator,采用雪花算法)。
  • ASSIGN_UUID:分配UUID,主键类型为String。使用接口IdentifierGenerator的方法nextUUID(默认实现为默认方法)。
  • ID_WORKER:分布式全局唯一ID长整型类型(建议使用ASSIGN_ID)。
  • UUID:32位UUID字符串(建议使用ASSIGN_UUID)。
  • ID_WORKER_STR:分布式全局唯一ID字符串类型(建议使用ASSIGN_ID)。

AUTO策略示例

当使用AUTO策略时,你需要确保数据库表的主键字段是自增的。

代码语言:java复制
@Data  
@AllArgsConstructor  
@NoArgsConstructor  
@TableName("sys_user")  
public class User {  
    @TableId(type = IdType.AUTO)  
    private Long id;  
    private String name;  
    private Integer age;  
    private String email;  
}  
  
// 测试方法  
@Test  
void testAutoPrimaryKey() {  
    User user = new User();  
    user.setName("Mary");  
    user.setAge(35);  
    user.setEmail("test7@powernode.com");  
    userMapper.insert(user); // 插入后,id字段会被自动赋值  
}

INPUT策略示例

使用INPUT策略时,你需要在插入数据前手动设置主键值。

代码语言:java复制
@Data  
@AllArgsConstructor  
@NoArgsConstructor  
@TableName("sys_user")  
public class User {  
    @TableId(type = IdType.INPUT)  
    private Long id;  
    private String name;  
    private Integer age;  
    private String email;  
}  
  
// 测试方法  
@Test  
void testInputPrimaryKey() {  
    User user = new User();  
    user.setId(1L); // 必须手动设置id  
    user.setName("Jerry");  
    user.setAge(38);  
    user.setEmail("test8@powernode.com");  
    userMapper.insert(user); // 插入成功,因为id已设置  
}

ASSIGN_ID策略示例

ASSIGN_ID策略使用雪花算法生成ID,适用于分布式环境。

代码语言:java复制
@Data  
@AllArgsConstructor  
@NoArgsConstructor  
@TableName("sys_user")  
public class User {  
    @TableId(type = IdType.ASSIGN_ID)  
    private Long id;  
    // ... 其他字段  
}  
  
// 测试方法(与AUTO策略类似,但ID由框架自动生成)  
@Test  
void testAssignIdPrimaryKey() {  
    User user = new User();  
    user.setName("John");  
    user.setAge(28);  
    user.setEmail("test9@powernode.com");  
    userMapper.insert(user); // 插入后,id字段会被自动赋值(雪花算法生成)  
}

ASSIGN_UUID策略示例

ASSIGN_UUID策略使用UUID算法生成主键,适用于需要全局唯一字符串ID的场景。

代码语言:java复制
@Data  
@AllArgsConstructor  
@NoArgsConstructor  
@TableName("sys_user")  
public class User {  
    @TableId(type = IdType.ASSIGN_UUID)  
    private String id; // 注意这里id的类型是String,以容纳UUID  
    private String name;  
    private Integer age;  
    private String email;  
}  
  
// 测试方法  
@Test  
void testAssignUuidPrimaryKey() {  
    User user = new User();  
    user.setName("Alice");  
    user.setAge(25);  
    user.setEmail("testA@powernode.com");  
    userMapper.insert(user); // 插入后,id字段会被自动赋值(UUID生成)  
      
    // 验证生成的UUID  
    String uuid = user.getId();  
    // 这里可以对uuid进行断言或者输出等操作  
    System.out.println("Generated UUID: "   uuid);  
}

ID_WORKER 和 ID_WORKER_STR 策略(已废弃)

请注意,ID_WORKER 和 ID_WORKER_STR 策略在Mybatis-Plus的较新版本中已经被废弃,建议使用 ASSIGN_ID 替代。ID_WORKER 和 ID_WORKER_STR 原本是基于Twitter的Snowflake算法实现的分布式唯一ID生成策略,但现在建议使用ASSIGN_ID,因为它提供了更灵活和可配置的ID生成方式。

自定义主键生成策略

如果你需要实现自定义的主键生成策略,可以实现 com.baomidou.mybatisplus.extension.incrementer.IdentifierGenerator 接口,并覆盖 nextIdnextUUID 方法。然后,你可以通过 @TableId 注解的 generator 属性指定你的自定义实现类。

代码语言:java复制
// 自定义主键生成器  
public class CustomIdGenerator implements IdentifierGenerator {  
    @Override  
    public Long nextId(Object entity) {  
        // 这里实现你的自定义ID生成逻辑  
        // ...  
        return yourCustomGeneratedId; // 返回你的自定义ID  
    }  
  
    @Override  
    public String nextUUID(Object entity) {  
        // 这里通常不会重写此方法,因为ASSIGN_UUID类型会使用默认的UUID生成策略  
        // ...  
        return null;  
    }  
}  
  
// 在实体类中使用自定义主键生成器  
@Data  
@AllArgsConstructor  
@NoArgsConstructor  
@TableName("sys_user")  
public class User {  
    @TableId(type = IdType.ASSIGN_ID, generator = "customIdGenerator")  
    private Long id;  
    // ... 其他字段  
  
    // 还需要在Mybatis-Plus的配置中注册你的自定义主键生成器  
    // 例如,在Spring Boot应用中,你可以在MybatisPlusConfig类中注册  
}  
  
// MybatisPlusConfig配置类示例(Spring Boot)  
@Configuration  
public class MybatisPlusConfig {  
  
    @Bean  
    public IdentifierGenerator customIdGenerator() {  
        return new CustomIdGenerator();  
    }  
  
    // ... 其他Mybatis-Plus配置  
}

0 人点赞