为什么工作 10 年都没遇过分布式锁?

沉默是金,总会发光

大家好,我是沉默

前两天在群里看到一句话,瞬间把我笑喷:

"工作10年了,简历上写了熟悉分布式系统,结果一次分布式锁都没用过。是太菜,还是公司太稳?"

底下一群人立刻跟上:

  • "+1,我也是!"

  • "我们公司连'分布'俩字都不敢提......"

  • "别说锁了,我们连 Redis 集群都没有,就一台单机 Redis 顶天。"

看到这里,我只想说一句:
兄弟,这不是你一个人的困惑,这是大部分开发的真实写照。

**-**01-

啥是分布式锁?

想象你跟 10 个人排队打饭------大家都很守规矩:先来先打,公平有序

但如果这 10 个人分散在不同窗口,每人都觉得"锅里还有"而同时开舀?

锅就穿了。

这就是分布式系统中的典型现象------多个节点抢一个资源,必须定规则,否则乱套。

分布式锁的用途就是:

  • 谁先抢到锁,谁执行
  • 执行完才允许下一个来

**

**

典型冲突场景:

  • 发红包不能发两次

  • 库存不能卖超

  • 定时任务不能多个节点一起跑

很多公司根本没这些高并发需求,所以你自然用不上。

- 02-

两个你肯定听过的真实事故

场景 1:秒杀超卖

活动喊着"限量 100 件",结果卖了 130 件。

仓库懵了,客服炸了,领导坐你后面看你写代码。

为什么会超卖?

因为有十台服务器同时判断:

"库存 > 0,那可以卖!"

于是......一起卖了。

解决方式: 在扣库存之前加锁,抢到锁才能操作。

** **

场景 2:重复退款

用户手速太快,"退款"点了两次。

你的服务部署在三个节点里,结果两个节点收到了同一个请求。

如果没锁?
资金直接退两遍。

- 03-

分布式锁咋实现?

Redis 分布式锁

原理不复杂,就是:

  • SETNX 抢锁
  • 设置过期时间避免死锁
  • 释放锁时判断是不是自己的锁

(SpringBoot 简化版):

typescript 复制代码
@Componentpublic class RedisDistributedLock {    @Autowired    private StringRedisTemplate redisTemplate;    public boolean tryLock(String lockKey, String requestId, long expireTime) {        return redisTemplate.opsForValue()            .setIfAbsent(lockKey, requestId, expireTime, TimeUnit.SECONDS);    }    public void releaseLock(String lockKey, String requestId) {        String currentValue = redisTemplate.opsForValue().get(lockKey);        if (requestId.equals(currentValue)) {            redisTemplate.delete(lockKey);        }    }}

看起来"像那么回事",但上生产就开始暴露坑:

  • 锁到期太短 → 业务还没执行完锁就失效

  • 锁到期太长 → 业务挂了锁一直不释放

  • 锁被别人抢走后,你把别人的锁释放了(灾难)

生产还得是 Redisson 分布式锁

Redisson:

"别怕,我都给你封装好了。"

自动续期(看门狗)、可重入锁、公平锁、读写锁,全都有。

** **

使用也很简单:

1)引依赖

xml 复制代码
<dependency>    <groupId>org.redisson</groupId>    <artifactId>redisson-spring-boot-starter</artifactId>    <version>3.24.1</version></dependency>

2)代码更简单

scss 复制代码
@Servicepublic class PaymentService {    @Autowired    private RedissonClient redissonClient;    public void processRefund(String orderNo) {        RLock lock = redissonClient.getLock("lock:refund:" + orderNo);        try {            boolean isLocked = lock.tryLock(100, 10, TimeUnit.SECONDS);            if (isLocked) {                if (hasRefunded(orderNo)) {                    throw new RuntimeException("已退款,请勿重复操作");                }                doRefund(orderNo);                recordRefund(orderNo);            }        } catch (Exception e) {            throw new RuntimeException("获取锁失败", e);        } finally {            if (lock.isHeldByCurrentThread()) {                lock.unlock();            }        }    }}

放心,这玩意能撑住大部分业务场景。

**-****04-**总结

为什么你没用过?

非常简单,只有两种原因:

❶ 公司业务稳得一匹

  • 用户量小
  • 单节点就够
  • 业务流程不冲突
  • 高并发压根不存在

没到量级,当然用不上。

❷ 框架和数据库帮你扛了

你以为没做,其实系统已经帮你做了:

  • MySQL 悲观锁:SELECT ... FOR UPDATE
  • 乐观锁:version字段
  • Redis INCR/DECR 原子操作
  • 消息去重

你"看上去没锁",但其实"锁无处不在"。

现在不用,不代表以后用不到

跳槽、业务增长、架构升级,都可能让你突然遇到分布式场景。

而分布式锁属于那种:

"线上十年不用,一次用不好就出大事故"的功能。

所以现在把原理搞明白、把代码跑通,未来一定能救你一命。

你工作几年?用过分布式锁吗?

你可以直接在评论区说说:

  • 你第一次用分布式锁是什么场景?

  • 你们公司是不是至今连 Redis 集群都没有?

  • 或者,你也是"写了分布式系统,但没见过分布式锁"的那种?

复制代码

**-****05-**粉丝福利

复制代码
站在职业的十字路口,我们或许都曾感到迷茫:




投出的简历总是没有回音?




面试时不知如何展现自己的优势?




未来的职场道路该如何规划?




技术管理能力提升,如何跨越第一步?




如果你正在经历这些,我很乐意用我的经验为你提供一些帮助。




无论是修改简历、1对1求职陪跑,职业规划咨询,




还是迈向技术Leader或提升管理效能,




欢迎你加我,我们像朋友一样聊聊。
相关推荐
中年程序员一枚8 小时前
多数据源的springboot进行动态连接方案
java·spring boot·后端
w***76558 小时前
SpringBoot集成MQTT客户端
java·spring boot·后端
HABuo8 小时前
【Linux进程(五)】进程地址空间深入剖析-->虚拟地址、物理地址、逻辑地址的区分
linux·运维·服务器·c语言·c++·后端·centos
编程饭碗8 小时前
【多线程编程】
java·开发语言
北鹿不麋鹿8 小时前
自学Java手记:Map集合,Arrays工具类和Lambda表达式
java
码头整点薯条8 小时前
对接第三方服务踩坑:属性大小写不匹配导致数据解析失败,一个注解搞定!
java
Wpa.wk8 小时前
性能测试工具 - JMeter工具组件介绍一
java·经验分享·测试工具·jmeter·性能测试
虫小宝8 小时前
个微iPad协议场景下Java后端的协议解析异常排查与问题定位技巧
java·svn·ipad
程序媛徐师姐8 小时前
Java基于微信小程序的鲜花销售系统,附源码+文档说明
java·微信小程序·鲜花销售小程序·java鲜花销售小程序·鲜花销售微信小程序·java鲜花销售系统小程序·java鲜花销售微信小程序
语落心生8 小时前
Deepseek-ai深夜开源Engram存算分离模块-技术解析与工程实践指南
架构