Skip to content

Commit

Permalink
初步完成分布式ID组件
Browse files Browse the repository at this point in the history
  • Loading branch information
javaKing-lgy committed Dec 31, 2024
1 parent 88eb019 commit 2163c42
Show file tree
Hide file tree
Showing 12 changed files with 359 additions and 0 deletions.
20 changes: 20 additions & 0 deletions douyu-live-id-generate-interface/pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.douyu</groupId>
<artifactId>douyu-live-app</artifactId>
<version>1.0-SNAPSHOT</version>
</parent>

<artifactId>douyu-live-id-generate-interface</artifactId>

<properties>
<maven.compiler.source>17</maven.compiler.source>
<maven.compiler.target>17</maven.compiler.target>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>

</project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package com.douyu.live.id.generate.interfaces;

/**
* id 生成接口
* @author luiguanyi
* * @date 2024/12/29
*/
public interface IdBuilderRpc {

/**
* 获取有序ID
* @param id
* @return
*/
Long getSeqId(Integer id);

/**
* 获取无序ID
* @param id
* @return
*/
Long getUnSeqId(Integer id);
}
56 changes: 56 additions & 0 deletions douyu-live-id-generate-provider/pom.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.douyu</groupId>
<artifactId>douyu-live-app</artifactId>
<version>1.0-SNAPSHOT</version>
</parent>

<artifactId>douyu-live-id-generate-provider</artifactId>

<properties>
<mybatis-plus.version>3.5.3</mybatis-plus.version>
<dubbo.version>3.2.0-beta.3</dubbo.version>
</properties>
<dependencies>
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>${mybatis-plus.version}</version>
</dependency>
<dependency>
<groupId>org.apache.dubbo</groupId>
<artifactId>dubbo-spring-boot-starter</artifactId>
<version>${dubbo.version}</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<exclusions>
<exclusion>
<artifactId>log4j-to-slf4j</artifactId>
<groupId>org.apache.logging.log4j</groupId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>${qiyu-mysql.version}</version>
</dependency>
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<dependency>
<groupId>com.douyu</groupId>
<artifactId>douyu-live-id-generate-interface</artifactId>
<version>1.0-SNAPSHOT</version>
<scope>compile</scope>
</dependency>
</dependencies>

</project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
package com.douyu.live.id.generate.provider.dao.mapper;

import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.douyu.live.id.generate.provider.dao.po.IdBuilderPO;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import org.apache.ibatis.annotations.Select;
import org.apache.ibatis.annotations.Update;

import java.util.List;

/**
* id 生成器配置表持久层
* @author luiguanyi
* * @date 2024/12/31
*/
@Mapper
public interface IdBuilderMapper extends BaseMapper<IdBuilderPO> {

/**
* 更新当前阈值 开始 以及版本
*/
@Update("UPDATE t_id_builder_config set next_threshold=#{nextThreshold},current_start=#{currentStart},vers ion=version+1 " +
"where id=#{id} and version=#{version}")
Integer updateCurrentThreshold(@Param("nextThreshold") long nextThreshold, @Param("currentStart") long currentStart,
@Param("id") int id, @Param("version") int version);

/**
* 查询所有配置
*/
@Select("select * from t_id_builder_config")
List<IdBuilderPO> selectAll();
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
package com.douyu.live.id.generate.provider.dao.po;

import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Data;
import java.util.Date;

/**
* id生成器配置表
* @author luiguanyi
* * @date 2024/12/31
*/
@TableName("t_id_builder_config")
@Data
public class IdBuilderPO {
@TableId(type = IdType.AUTO)
private Integer id;
/**
* id 备注描述
*/
private String remark;
/**
* 初始化值
*/
private long initNum;
/**
* 步长
*/
private int step;
/**
* 是否是有序的id
*/
private int isSeq;
/**
* 当前id 所在阶段的开始值
*/
private long currentStart;
/**
* 当前id 所在阶段的阈值
*/
private long nextThreshold;
/**
* 业务代码前缀
*/
private String idPrefix;
/**
* 乐观锁版本号
*/
private int version;
/**
* 创建时间
*/
private Date createTime;
/**
* 更新时间
*/
private Date updateTime;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package com.douyu.live.id.generate.provider.rpc;

import com.douyu.live.id.generate.interfaces.IdBuilderRpc;
import org.apache.dubbo.config.annotation.DubboService;

/**
* id 生成 rpc 实现
* @author luiguanyi
* * @date 2024/12/29
*/
@DubboService
public class IdBuilderRpcImpl implements IdBuilderRpc {
@Override
public Long getSeqId(Integer id) {
return null;
}

@Override
public Long getUnSeqId(Integer id) {
return null;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package com.douyu.live.id.generate.provider.service;

/**
* id生成服务
* @author luiguanyi
* * @date 2024/12/29
*/
public interface IdGenerateService {
/**
* 生成有序id
*
* @param code
* @return
*/
Long getSeqId(Integer code);
/**
* 生成无序id
*
* @param code
* @return
*/
Long getUnSeqId(Integer code);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
package com.douyu.live.id.generate.provider.service.bo;

import lombok.Data;

import java.util.concurrent.atomic.AtomicLong;

/**
* 本地id生成的一个具体策略
* @author luiguanyi
* * @date 2024/12/29
*/
@Data
public class LocalSeqIdBO {

/**
* 业务ID
*/
private int id;


/**
* 在内存中记录的当前的值
*/
private AtomicLong currentNum;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
package com.douyu.live.id.generate.provider.service.impl;

import com.douyu.live.id.generate.provider.dao.mapper.IdBuilderMapper;
import com.douyu.live.id.generate.provider.dao.po.IdBuilderPO;
import com.douyu.live.id.generate.provider.service.IdGenerateService;
import com.douyu.live.id.generate.provider.service.bo.LocalSeqIdBO;
import jakarta.annotation.PostConstruct;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.atomic.AtomicLong;

/**
* id生成服务实现
* @author luiguanyi
* * @date 2024/12/29
*/
@Service
@Slf4j
public class IdGenerateServiceImpl implements IdGenerateService {

@Resource
private IdBuilderMapper idBuilderMapper;

private static final Map<Integer, LocalSeqIdBO> localSeqIdMap = new ConcurrentHashMap<>();



@Override
public Long getSeqId(Integer id) {
if(id == null){
log.error("[getSeqId] id is error");
return null;
}
LocalSeqIdBO localSeqIdBO = localSeqIdMap.get(id);
if(localSeqIdBO == null){
log.error("[getSeqId] localSeqIdBo is null ,id is {}",id);
return null;
}
return localSeqIdBO.getCurrentNum().getAndIncrement();
}

@Override
public Long getUnSeqId(Integer code) {
return null;
}

/**
* 初始化我们的localSeqIdMap
*/
@PostConstruct
public void init(){
List<IdBuilderPO> idBuilderPOS = idBuilderMapper.selectAll();
idBuilderPOS.forEach(idBuilderPO -> {
// 进行更新数据库中当前id 的配置 就是修改表中当前的id段 往后面挪一个步长
Integer updateResult = idBuilderMapper.updateCurrentThreshold(idBuilderPO.getNextThreshold(), idBuilderPO.getNextThreshold() + idBuilderPO.getStep(), idBuilderPO.getId(), idBuilderPO.getVersion());
if (updateResult == 0){
IdBuilderPO newIdBuilderPO = idBuilderMapper.selectById(idBuilderPO.getId());
}
LocalSeqIdBO localSeqIdBO = new LocalSeqIdBO();
localSeqIdBO.setId(idBuilderPO.getId());
localSeqIdBO.setCurrentNum(new AtomicLong(idBuilderPO.getCurrentStart()));
localSeqIdMap.put(idBuilderPO.getId(),localSeqIdBO);
});
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
spring:
application:
name: douyu-live-id-generate-provider
datasource:
driver-class-name: com.mysql.cj.jdbc.Driver
#访问主库
url: jdbc:mysql://127.0.0.1:3306/douyu_live_common?useUnicode=true&characterEncoding=utf8
username: root
password: root

dubbo:
application:
name: ${spring.application.name}
registry:
address: nacos://127.0.0.1:8848?namespace=douyu-live-test&&username=nacos&&password=nacos
protocol:
name: dubbo
port: 9098
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
spring:
cloud:
nacos:
username: nacos
password: nacos
discovery:
server-addr: 127.0.0.1:8848
namespace: douyu-live-test
2 changes: 2 additions & 0 deletions pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,8 @@
<module>douyu-live-api</module>
<module>douyu-live-common-interface</module>
<module>douyu-live-framework</module>
<module>douyu-live-id-generate-interface</module>
<module>douyu-live-id-generate-provider</module>
</modules>

<properties>
Expand Down

0 comments on commit 2163c42

Please sign in to comment.