获取全局的ID,方法有很多,常见的有几个,这都是网上说烂了的东西
-
Snowflake
雪花算法 - UUID
- Redis自增
- 数据库自增
- …
各有各的好处弊端,自己酌情而定。这里介绍一个很简单的办法,是基于数据库ID生成器。
DataFieldMaxValueIncrementer
spring-jdbc
提供的一个工具类接口,它定义了3个获取下一个ID
的方法。
public interface DataFieldMaxValueIncrementer {
int nextIntValue() throws DataAccessException;
long nextLongValue() throws DataAccessException;
String nextStringValue() throws DataAccessException;
}
主要有2个实现
AbstractSequenceMaxValueIncrementer
使用标准的数据库序列产生主键值
AbstractColumnMaxValueIncrementer
使用一张模拟序列的表产生主键值
其中MSQL的实现
MySQLMaxValueIncrementer
MySQLMaxValueIncrementer 的配置使用
MySQLDataFieldMaxValueIncrementer
import javax.sql.DataSource;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.jdbc.support.incrementer.DataFieldMaxValueIncrementer;
import org.springframework.jdbc.support.incrementer.MySQLMaxValueIncrementer;
@Configuration
public class MySQLDataFieldMaxValueIncrementer {
@Bean
public DataFieldMaxValueIncrementer dataFieldMaxValueIncrementer (@Autowired DataSource dataSource) {
MySQLMaxValueIncrementer mySQLMaxValueIncrementer = new MySQLMaxValueIncrementer();
/**
* 数据源
*/
mySQLMaxValueIncrementer.setDataSource(dataSource);
/**
* 维护序列的表名
*/
mySQLMaxValueIncrementer.setIncrementerName("id_table");
/**
* 维护序列表中的列名
*/
mySQLMaxValueIncrementer.setColumnName("id");
/**
* 字符串结果的填充长度,不足长度会在前面填充0
*/
mySQLMaxValueIncrementer.setPaddingLength(10);
/**
* 是否每次操作都是使用新的链接,默认为true
*/
mySQLMaxValueIncrementer.setUseNewConnection(false);
/**
* 设置缓存主键的个数,当内存中主键值用完后,递增器将一次性获取cacheSize个主键
*/
mySQLMaxValueIncrementer.setCacheSize(1);
return mySQLMaxValueIncrementer;
}
}
表结构
CREATE TABLE `id_table` (
`id` int(10) unsigned NOT NULL COMMENT 'id',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;
数据表创建后id
不能为null
,必须先初始化一个值(建议:0
),不然多次获取返回的结果都是:0
使用
@Autowired
private DataFieldMaxValueIncrementer dataFieldMaxValueIncrementer;
@Test
public void test () {
int val = this.dataFieldMaxValueIncrementer.nextIntValue();
System.out.println(val); // 1
String strVal = this.dataFieldMaxValueIncrementer.nextStringValue();
System.out.println(strVal); // 0000000002
}