热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

SpringCloud电商秒杀微服务Redisson分布式锁方案

一、引言:前两篇文章,介绍了:《学会Zookeeper分布式锁--让面试官对你刮目相看》《SpringBoot电商项目实战-Cura

一、引言:

前两篇文章,介绍了:

《学会Zookeeper分布式锁--让面试官对你刮目相看》

《SpringBoot电商项目实战-Curator分布式锁实现》

细心的读者可能发现,号主在分布式锁这条路上“越走越黑”,已经发表了好几篇相关文章了,莫慌,再学完本章,你就可以在分布式锁场景下拿着倚天剑与屠龙刀叱咤分风云了

因为实际项目可能面临各种业务场景需求,需要不同的分布式锁方案,而这些文章并不是类似网上很多的教你ctrl c  + ctrl +v,关键掌握真谛。还不会的建议先去看下第一篇哦,从实际高并发场景深入浅出,层层剖析...

1、分布式锁思路分析

锁特点:


  • 排他性:同一时间,只有一个线程能获得;

  • 阻塞性:其它未抢到的线程阻塞等待,直到锁被释放,再继续抢;

  • 可重入性:线程获得锁后,后续是否可重复获取该锁(避免死锁)。

当然,还要考虑性能开销等问题。

2、常规的分布式锁解决方案有哪几种:


  • 文件系统:同一个目录下,不能存在同名文件

  • 数据库锁:主键 、 唯一约束  、for  update

  • 基于Redis的分布式锁:setnx、set、Redisson

  • 基于ZooKeeper的分布式锁:类似文件系统

直接进入今天正题,就不多介绍分布式锁的背景、区别之类了,可以参考前两篇文章哦。



二、redis分布式锁简介

1、基于redis分布式锁

(1)基本锁


  • 原理:利用redis的setnx,如果不存在某个key则设置值,设置成功则表示取得锁成功。

  • 缺点:如果获取锁后的进程在没有执行完就挂了,则锁永远不会释放,产生死锁。

(2)改进型


  • 改进:在基本锁上setnx后设置expire,保证超时后也能自动释放锁。

  • 缺点:setnx与expire不是一个原子操作,可能执行完setnx,还没来得及执行expire设置过期时间,该进程就挂了。

(3)增强版


  • 改进:利用Lua脚本,将setnx与expire变成一个原子操作,可解决一部分问题。

  • 缺点:还是锁过期问题。

注意: Redis 从2.6.12版本开始 set 命令支持 NX 、 PX 这些参数来达到 setnx 、 setex 、 psetex 命令的效果。

2、Redisson简介

所以直接使用redis自己实现分布式锁,相对麻烦,还存在上面的问题。接下来主要分析Redisson的分布式锁的实现,一般提及到Redis的分布式锁我们更多的使用的是Redisson的分布式锁,Redis的官方也是建议我们这样去做的。Redisson点我可以直接跳转到Redisson的官方文档。



注:redisson 更新注意点


  • 2018-02-26更新:增加tryLock方法,建议后面去掉DistributedLocker接口和其实现类,直接在RedissLockUtil中注入RedissonClient实现类(简单但会丢失接口带来的灵活性)。

  • 2019-07-11更新:redisson官方发布了 redisson-spring-boot-starter

本文将引入最新的redisson和springboot的集成包:redisson-spring-boot-starter,网上的很多教程可能还是使用redisson老版本,互相copy。redisson介绍可参考官网,有中英文wiki 。

 

参考官网:

https://github.com/redisson/redisson/tree/master/redisson-spring-boot-starter#spring-boot-starter



注:本示例为方便演示,仅提供如何实现redisson分布式锁方案,库存直接读取数据库,自己可以改造放到redis等缓存中,这个不会的自己去脑补。

三、项目实战

1、添加依赖:

org.redisson redisson-spring-boot-starter 3.11.2

2、application.yml配置

3、redissson.yml 配置

4、新建一个redisson配置,读取配置文件redisson.yml,并将RedissonClient注册到spring ioc容器

@Configurationpublic class RedissonConfig { @Bean(destroyMethod = "shutdown") public RedissonClient redisson() throws IOException { // 1. 创建Config对象,读取配置属性 // 2. 创建Redisson对象,传入Config对象 RedissonClient redisson = Redisson.create(Config.fromYAML( new ClassPathResource("redisson.yml").getInputStream())); return redisson; }}

5、新建一个商品服务实现类

@Servicepublic class ProductServiceImpl implements IProductService { @Autowired    private ProductDao productDao; @Autowired    private RedissonClient redissonClient; /** * 秒杀商品 * @param productId 商品ID * @param number 数量 * @return */ @Override public Boolean seckillProduct(Long productId, Integer number) { String key = "seckill_stock_lock_" + productId; RLock lock = redissonClient.getLock(key); try { //获取分布式锁 lock.lock(); Product product = productDao.selectById(productId); if ( product!=null && product.getStocks() == 0) { return false; } Integer stocks = product.getStocks() - 1; productDao.updateStocksById(productId,stocks); } catch (Exception e) { e.printStackTrace(); } finally { lock.unlock(); } return true; }}

6、新建一个controller,并提供一个http接口:秒杀商品

@RestController@RequestMapping("/product")public class ProductController { @Autowired private IProductService productService; /** * 秒杀商品测试 * @return */ @GetMapping("seckillTest") public String seckillProductTest() { Boolean flag = productService.seckillProduct(1L, 1); if(flag ==true){ return "创建订单成功"; } else{ return "库存不足"; } }}

7、数据库product商品表数据如下,id=1的库存为30个,如下:

8、使用并发测试工具类,如jmeter ,新建一个测试任务,并发线程设为50或其他,模拟多人同时并发秒杀某个商品,启动项目,然后测试:

9、全部执行成功后,查看数据库中数据,库存已经为0,没有出现负数,超卖的情况。

完结,分布式锁专题终于告一段落,你学会了吗

注:本示例为方便演示,仅提供如何实现redisson分布式锁方案,库存直接读取数据库,自己可以改造放到redis等缓存中,这个不会的自己去脑补。

●SpringBoot电商项目实战-Curator分布式锁实现

●学会Zookeeper分布式锁,让面试官对你刮目相看

●SpringBoot+Token实现接口幂等性|防止表单重复提交

一只 有深度 有灵魂 的公众号0.0  "阿甘正专"

来都来了,点个在看再走吧~~~


推荐阅读
  • 优化后的标题:深入探讨网关安全:将微服务升级为OAuth2资源服务器的最佳实践
    本文深入探讨了如何将微服务升级为OAuth2资源服务器,以订单服务为例,详细介绍了在POM文件中添加 `spring-cloud-starter-oauth2` 依赖,并配置Spring Security以实现对微服务的保护。通过这一过程,不仅增强了系统的安全性,还提高了资源访问的可控性和灵活性。文章还讨论了最佳实践,包括如何配置OAuth2客户端和资源服务器,以及如何处理常见的安全问题和错误。 ... [详细]
  • 秒建一个后台管理系统?用这5个开源免费的Java项目就够了
    秒建一个后台管理系统?用这5个开源免费的Java项目就够了 ... [详细]
  • 可参照github代码:https:github.comrabbitmqrabbitmq-tutorialsblobmasterjavaEmitLogTopic.ja ... [详细]
  • 在本篇学习指南中,我们将探讨 Spring Cloud 2020 版本中的技术选型和版本选择策略。具体来说,我们将详细介绍如何在项目中选用 Spring Boot 和 Spring Cloud 的最佳组合。本文以 Spring Boot 2.2.2 为例,结合实际应用场景,提供详细的配置和使用建议,帮助开发者更好地理解和应用这些框架。此外,我们还将讨论不同版本之间的兼容性和升级路径,确保项目能够平稳过渡到最新版本。 ... [详细]
  • 本文深入解析了Spring Cloud路由网关Zuul的核心功能及其典型应用场景。通过对方志朋老师教材的学习和实践,详细探讨了Zuul在微服务架构中的重要作用,包括请求路由、过滤器链管理以及服务动态扩展等关键特性。同时,结合实际案例,展示了Zuul在高并发和复杂业务场景下的应用优势,为读者提供了全面的技术参考。 ... [详细]
  • CentOS 7环境下Jenkins的安装与前后端应用部署详解
    CentOS 7环境下Jenkins的安装与前后端应用部署详解 ... [详细]
  • 如何在Windows上使用Gitee创建远程仓库
    本文详细记录了在Windows系统上使用Gitee创建远程仓库的步骤,帮助解决无法注册GitHub的问题。 ... [详细]
  • 浅析python实现布隆过滤器及Redis中的缓存穿透原理_python
    本文带你了解了位图的实现,布隆过滤器的原理及Python中的使用,以及布隆过滤器如何应对Redis中的缓存穿透,相信你对布隆过滤 ... [详细]
  • 命令模式是一种行为设计模式,它将请求封装成一个独立的对象,从而允许你参数化不同的请求、队列请求或者记录请求日志。本文将详细介绍命令模式的基本概念、组件及其在实际场景中的应用。 ... [详细]
  • 【实例简介】本文详细介绍了如何在PHP中实现微信支付的退款功能,并提供了订单创建类的完整代码及调用示例。在配置过程中,需确保正确设置相关参数,特别是证书路径应根据项目实际情况进行调整。为了保证系统的安全性,存放证书的目录需要设置为可读权限。值得注意的是,普通支付操作无需证书,但在执行退款操作时必须提供证书。此外,本文还对常见的错误处理和调试技巧进行了说明,帮助开发者快速定位和解决问题。 ... [详细]
  • Spring Cloud 学习指南:初学者入门篇
    Spring Cloud 学习指南:初学者入门篇 ... [详细]
  • 在PHP中实现腾讯云接口签名,以完成人脸核身功能的对接与签名配置时,需要注意将文档中的POST请求改为GET请求。具体步骤包括:使用你的`secretKey`生成签名字符串`$srcStr`,格式为`GET faceid.tencentcloudapi.com?`,确保参数正确拼接,避免因请求方法错误导致的签名问题。此外,还需关注API的其他参数要求,确保请求的完整性和安全性。 ... [详细]
  • 技术日志:使用 Ruby 爬虫抓取拉勾网职位数据并生成词云分析报告
    技术日志:使用 Ruby 爬虫抓取拉勾网职位数据并生成词云分析报告 ... [详细]
  • K3Cloud 平台字符串解密技术详解与应用
    在 K3Cloud 平台中,配置文件内的敏感信息如密码会被加密处理。通过深入研究,我们发现可以通过 Kingdee.BOS.Api 提供的接口对这些加密字符串进行解密。本文详细介绍了这一解密技术的具体实现方法及其应用场景,为开发者提供了宝贵的参考和实践指导。此外,还探讨了该技术在数据安全和系统管理中的重要性,以及如何在实际项目中高效地应用这些技术,确保系统的稳定性和安全性。 ... [详细]
  • 近年来,BPM(业务流程管理)系统在国内市场逐渐普及,多家厂商在这一领域崭露头角。本文将对当前主要的BPM厂商进行概述,并分析其各自的优势。目前,市场上较为成熟的BPM产品主要分为两类:一类是综合型厂商,如IBM和SAP,这些企业在整体解决方案方面具有明显优势;另一类则是专注于BPM领域的专业厂商,它们在特定行业或应用场景中表现出色。通过对比分析,本文旨在为企业选择合适的BPM系统提供参考。 ... [详细]
author-avatar
菜鸟一号
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有