库存扣减避免超卖
# 利用数据库的原子操作(推荐)
update inventory
set quantity = quantity - #{count}
where sku_id='123' and quantity >= #{count}
1
2
3
2
3
正常来说,MySQL的热点行更新最多也就抗200-300的并发更新,如果想要抗的更多,就得提升硬件水平
# Redis + Lua 脚本(高并发场景)
local key = KEYS[1] -- 商品的键名
local amount = tonumber(ARGV[1]) -- 扣减的数量
-- 获取商品当前的库存量
local stock = tonumber(redis.call('get', key))
-- 如果库存足够,则减少库存并返回新的库存量
if stock >= amount then
redis.call('decrby', key, amount)
return redis.call('get', key)
else
return "INSUFFICIENT STOCK"
end
1
2
3
4
5
6
7
8
9
10
11
12
13
2
3
4
5
6
7
8
9
10
11
12
13
需要保证 Redis 和数据库库存一致性(可通过异步扣减或定时同步)
# 为什么不用分布式锁
没必要,我们用 lua 脚本,可以直接用利用他的原子性特性,在一个脚本中实现库存的检查、扣减等动作。
如果使用分布式锁,在不使用 lua 脚本的情况下,每次库存扣减操作都需要多次与 Redis 服务器通信(例如,加锁、读取库存、扣减库存、释放锁等)。这不仅增加了网络延时,还增加了系统的复杂性。
编辑 (opens new window)
上次更新: 2025-10-13 14:26:37