学会用数据说话-分布式锁究竟可以多少并发?

程序员萌萌在浏览关于分布式锁的文章,突然下面的话引起了萌萌的注意:

在锁操作的客户端打日志

获取锁:

T13:31:51.230redisname-lock:hsetnx

E13:31:51.230GetConnection10.X.X.X

T13:31:51.231redisname-lock:hsetnx

设置超时时间:

T13:31:51.230redisname-lock:hsetnx

E13:31:51.230GetConnection10.X.X.X

T13:31:51.231redisname-lock:hsetnx

释放锁:

T13:31:51.230redisname-unlock:hsetnx

E13:31:51.230GetConnection10.X.X.X

T13:31:51.231redisname-unlock:hsetnx

从上面数据可以看到一个正常分布式锁操作,操作时间在1ms,因为是从客户端获取的,因为粒度只能是毫秒级。再从服务端看看是什么情况。

上面显示了大于1ms的慢查询情况,可以看到每秒几百个的QPS不会造成分布式锁本身的慢查询。耗时超过1ms的都是集群操作,分布式锁的lock和unlock操作时间都是us级。

    如果lock和unlock中间没有任何逻辑的理想情况下,同一个锁可以支持每秒:

   1000ms/ (1ms的lock+1ms的设置超时+1ms的unlock)=333(个)

结论

分布式锁本身lock和unlock耗时是us级,在理想情况下大概可支持每秒1000个原子操作,300多个从分配到释放流程结束。

举个栗子?:

秒杀场景下,秒杀的产品有1000件。如果使用了分布式锁,理想情况下可以在1m内处理完所有的秒杀成功请求,其他请求直接返回秒杀结束。

既然秒杀都没有问题,一般情况下,分布式锁不会是性能瓶颈。如果出现了性能问题,首先先排查业务逻辑。

目录

1:一个线程里lock成功,unlock失败?

2:有哪些抓手可以确定哪些逻辑耗时太多?

3:锁内部要避免的操作有哪些?

4:循环获取锁的时间间隔怎么算合理?

5:获取锁重试次数怎么算合理?

6:多次获取锁失败原因有哪些?

7:加了分布式锁还出现了并发问题?

1:一个线程里lock成功,unlock失败?

Q: 日志里报了多次的unlock失败,什么原因?

A: 之前的代码里try finally模式的unlock,是否lock成功都会unlock。

Q:加上了lock成功才unlock,还是有unlock失败?

A:这是锁住的逻辑耗时太多,超过了expire的时间,自动释放锁了。

2:有哪些抓手可以确定哪些逻辑耗时太多?

Q: 日志可以吗?

A: 目前的日志可以找到有问题的traceId,看整个链路都进行了哪些处理,大概几步时间消耗,但是具体sql的耗时分析没有

Q:CAT监控可以吗?

A:CAT监控可以找到耗时多的几个请求,看到每条sql的耗时情况,超过5秒的sql都是需要注意的

3:锁内部要避免的操作有哪些?

Q:逻辑上的?

A:避免显式的和隐式的循环。如:.stream().

Q:性能上的?

A:数据查询的条件是否建立了索引

4:循环获取锁的时间间隔怎么算合理?

A:获取锁与服务器通讯时间可以忽略不计,在跨机房的情况下理论上也不超过2ms

所以锁可以获取到的时间=一段分布式锁中间执行时间平均值

5:获取锁重试次数怎么算合理?

A:获取锁的重试次数理论上如果获取锁时间间隔合理的话,就与允许的同时扩容最大容器数接近,不大于最大容器数20%。

6:多次获取锁失败原因有哪些?

A:如果不符合可获取到的时间间隔计算,则考虑是否特定场景下有耗时操作。具体可参考 3:锁内部要避免的操作有哪些?

7:加了分布式锁还出现了并发问题?

Q:锁获取失败是怎么处理的?

A:锁获取失败并没有按请求失败处理,而是在无锁状态下继续执行会引发并发问题。

Q:锁获取成功了还是出现并发问题?

A:执行太慢了,超过了expire的时间锁失效了。

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏程序员的SOD蜜

PDF.NET开发框架“内存数据库”架构设计

前一段时间,我写了篇《移花接木:当泛型方法遇上抽象类----我的“内存数据库”诞生记 》,记录了PDF.NET内存数据库的设计过程,最近做了些小改动,已经投入生...

31470
来自专栏Java后端技术

Centos7下安装redis实战(单机版以及集群)

  因项目需要,要引入redis做缓存,就在centos7下亲自安装了一遍redis,刚好趁着这个机会就来把redis的概念以及单机版和集群版redis安装步骤...

10610
来自专栏SeanCheney的专栏

Python的线程与进程

看过《Python分布式计算》,觉得线程和进程,最大的区别还是在于 —— 二者是如何与内存交互的。线程是共享式的内存架构,进程是分布式的内存架构,这才是问题的...

36780
来自专栏人工智能

带你构建你的的第一个Python和Django应用程序

群内不定时分享干货,包括最新的python企业案例学习资料和零基础入门教程,欢迎初学和进阶中的小伙伴入群学习交流 ? 您以前可能听说过Python,特别是如果您...

26150
来自专栏魏艾斯博客www.vpsss.net

如何使用 MAMP 快速搭建 php 环境

46450
来自专栏BeJavaGod

不错位的 java .class 反编译工具推荐

我们经常会反编译看一些class文件,但是反编译出来的文件里面会有很多杂乱的东西 一直以来都是用的idea来反编译的,只要把class文件往里面一拖就行了 这么...

55050
来自专栏云瓣

打包优化实践(如何Code Spliting)

开发环境中可使用 analyze-webpack-plugin 观察各模块的占用情况。以该项目为例:浏览器中输入 http://localhost:3000/a...

13920
来自专栏程序猿

面试问题之mysql修改哪些配置文件可以进行优化?

配置文件中具体修改的内容是什么呢?要是面试官问你,你该怎么回答?你想下,你坐在一间屋子里。 服务器的mysql性能优化,有两个大...

31970
来自专栏IMWeb前端团队

Express使用手记:核心入门

本文作者:IMWeb 陈映平 原文出处:IMWeb社区 未经同意,禁止转载 入门简介 ? Express是基于nodejs的web开发框架。优点是易上...

22560
来自专栏架构师之路

缓存与数据库一致性保证

本文主要讨论这么几个问题: (1)啥时候数据库和缓存中的数据会不一致 (2)不一致优化思路 (3)如何保证数据库与缓存的一致性 一、需求缘起 上一篇《缓存架构设...

700100

扫码关注云+社区

领取腾讯云代金券