在线时间:8:00-16:00
迪恩网络APP
随时随地掌握行业动态
扫描二维码
关注迪恩网络微信公众号
分布式系统全局唯一ID在互联网系统中,并发越大的系统,数据就越大,数据越大就越需要分布式,而大量的分布式数据就越需要唯一标识来识别它们。 例如淘宝的商品系统有千亿级别商品,订单系统有万亿级别的订单数据,这些数据都是日渐增长,传统的单库单表是无法支撑这种级别的数据,必须对其进行分库分表;一旦分库分表,表的自增ID就失去了意义;故需要一个全局唯一的ID来标识每一条数据(商品、订单)。 e.g: 一张表1亿条数据,被分库分表10张表,原先的ID就失去意义,所以需要全局唯一ID来标识10张表的数据。 全局唯一的ID生成的技术方案有很多,业界比较有名的有 UUID、Redis、Twitter的snowflake算法、美团Leaf算法。 基于Redis INCR 命令生成分布式全局唯一IDINCR 命令主要有以下2个特征:
基于以上2个特性,可以采用INCR命令来实现分布式全局ID生成。 采用Redis生成商品全局唯一IDProject Directory Maven Dependency <?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"> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>2.2.8.RELEASE</version> <relativePath/> </parent> <modelVersion>4.0.0</modelVersion> <groupId>org.fool.redis</groupId> <artifactId>redis-string-id</artifactId> <version>1.0-SNAPSHOT</version> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-redis</artifactId> </dependency> <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <version>1.18.12</version> </dependency> </dependencies> <build> <plugins> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> </plugin> </plugins> </build> </project> application.properties spring.application.name=redis-spring-id server.port=8888 spring.redis.host=localhost spring.redis.port=6379 spring.redis.database=0 spring.redis.password= spring.redis.timeout=2000 spring.redis.pool.max-active=10 spring.redis.pool.max-wait=1000 spring.redis.pool.max-idle=10 spring.redis.pool.min-idle=5 spring.redis.pool.num-tests-per-eviction-run=1024 spring.redis.pool.time-between-eviction-runs-millis=30000 spring.redis.pool.min-evictable-idle-time-millis=60000 spring.redis.pool.soft-min-evictable-idle-time-millis=10000 spring.redis.pool.test-on-borrow=true spring.redis.pool.test-while-idle=true spring.redis.pool.block-when-exhausted=false SRC Application.java package org.fool.redis; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; @SpringBootApplication public class Application { public static void main(String[] args) { SpringApplication.run(Application.class, args); } } Product.java package org.fool.redis.model; import lombok.Data; import java.math.BigDecimal; @Data public class Product { private Long id; private String name; private BigDecimal price; private String detail; } IdGeneratorService.java package org.fool.redis.service; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.data.redis.core.StringRedisTemplate; import org.springframework.stereotype.Service; @Service public class IdGeneratorService { @Autowired private StringRedisTemplate stringRedisTemplate; private static final String ID_KEY = "id:generator:product"; public Long incrementId() { return stringRedisTemplate.opsForValue().increment(ID_KEY); } } ProductController.java package org.fool.redis.controller; import lombok.extern.slf4j.Slf4j; import org.fool.redis.model.Product; import org.fool.redis.service.IdGeneratorService; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.RequestBody; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; @RestController @Slf4j @RequestMapping(value = "/product") public class ProductController { @Autowired private IdGeneratorService idGeneratorService; @PostMapping(value = "/create") public String create(@RequestBody Product obj) { //生成分布式id long id = idGeneratorService.incrementId(); //使用全局id 代替数据库的自增id obj.setId(id); //取模(e.g: 这里分为8张表,海量数据可以分为1024张表),计算表名 int table = (int) id % 8; String tableName = "product_" + table; log.info("insert to table: {}, with content: {}", tableName, obj); return "insert to table: " + tableName + " with content: " + obj; } } Test curl --location --request POST 'http://localhost:8888/product/create' \ --header 'Content-Type: application/json' \ --data-raw '{ "name": "Car", "price": "300000.00", "detail": "Lexus Style" }' Console Output 到此这篇关于Redis生成分布式系统全局唯一ID的实现的文章就介绍到这了,更多相关Redis生成分布式系统全局唯一ID内容请搜索极客世界以前的文章或继续浏览下面的相关文章希望大家以后多多支持极客世界! |
请发表评论