Redis生成分布式系统全局唯一ID的实现
在互联网系统中,并发越大的系统,数据就越大,数据越大就越需要分布式,而大量的分布式数据就越需要唯一标识来识别它们。
例如淘宝的商品系统有千亿级别商品,订单系统有万亿级别的订单数据,这些数据都是日渐增长,传统的单库单表是无法支撑这种级别的数据,必须对其进行分库分表;一旦分库分表,表的自增ID就失去了意义;故需要一个全局唯一的ID来标识每一条数据(商品、订单)。
e.g: 一张表1亿条数据,被分库分表10张表,原先的ID就失去意义,所以需要全局唯一ID来标识10张表的数据。
全局唯一的ID生成的技术方案有很多,业界比较有名的有 UUID、Redis、Twitter的snowflake算法、美团Leaf算法。
基于Redis INCR 命令生成分布式全局唯一IDINCR 命令主要有以下2个特征:
Redis的INCR命令具备了“INCR AND GET”的原子操作 Redis是单进程单线程架构,INCR命令不会出现ID重复基于以上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内容请搜索以前的文章或继续浏览下面的相关文章希望大家以后多多支持!
我想要获取技术服务或软件
服务范围:MySQL、ORACLE、SQLSERVER、MongoDB、PostgreSQL 、程序问题
服务方式:远程服务、电话支持、现场服务,沟通指定方式服务
技术标签:数据恢复、安装配置、数据迁移、集群容灾、异常处理、其它问题
本站部分文章参考或来源于网络,如有侵权请联系站长。
数据库远程运维 Redis生成分布式系统全局唯一ID的实现
相关文章
- 红色十分:Redis究竟能做什么(redis常用场景)
- Redis: 一款功能强大的NoSQL数据库(redis干嘛用的)
- 监控利用Redis实现实时状态监控(redis状态)
- Redis:卓越的内存数据库方案(redis内存数据库)
- 机制使用 Java 和 Redis 实现复杂数据过期机制(redisjava过期)
- 管理接口数据存储到Redis中(接口数据放到redis)
- 基于VC和Redis的异步任务队列实现研究(vc redis 队列)
- 配置VC6集成Redis实现可靠的扩展配置(vc6 redis 扩展)
- 调整 ulimit 对 Redis 最佳性能的重要性(ulimit redis)
- 如何实现Redis分片存储技术(如何实现redis分片)
- 使用Redis客户端实现数据存储管理(使用redis客户端)
- 基于Redis的多步骤实时监控(基于redis实现监听)
- 提升Redis最大存储能力的简介(redis默认最大存储)
- 从Redis默认大小中更好地使用它(redis 默认大小)
- 重构网络Redis实现高可用与高并发(redis高可用高并发)
- Redis集群扩容指南从准备到实施(redis集群扩容过程)
- Redis阻塞性能监控实践(redis 阻塞监控)
- Redis中的边查询边修改实用技巧(redis边查询边修改)
- 使用 Redis 超时处理技术实现更优性能(redis 超时解决方法)
- Redis实现安全用户密码设置(redis 设置用户密码)
- 实现Redis集群JWT的绝佳认证安全系统(redis集群jwt)
- Redis实现高效的Key存储策略(redis设置key策略)
- Redis实现轻松的持久层(redis落持久层)