扣减库存策略采用订单是否锁定库存方案
在订单系统中用户下订单流程中,有一个重要环节是“扣减库存”;而此“扣减库存”采用的策略是直接在一个商品库存字段中的库存数据减去订单商品数量;如:
update productStock set
quantity = quantity -1
where productId = 20034 and quantity >=1
此策略在高并发环境下会产生严重的性能问题。
所以本人就想换一种不争用同一行同一个字段的资源来避免竟争,以解决高并发带来的性能问题。本人的思路是,先将用户提交的订单插入订单表,然后获取此商的品原始投入的库存数,再取此产品已经被锁定库存的商品数量,将两者的数据与新下订单的商品数量比较,如果还可以再将此新订单锁定库存则更新这个订单的状态以表示此订单已经成功锁定库存。
sql 如下:
update [orderInfo]
set [IsEnabled] = 1
from [orderInfo] a
where a.orderid = 64434398158878 and a.Productid = 324285 and [IsEnabled] = 0 and a.ProductQTY <=(
select sum(QTY) from (
select StockQTY as QTY from [productStock] where Productid = 324285
union
select -sum( ProductQTY ) as QTY
from [orderInfo]
where Productid = 324285 and [IsEnabled] = 1
) as p
)
这样,更新数据的行为是更新每个订单记录的状态,不存在资源的竞争问题,也将大大提高性能。
当然,这要求所有的订单数据都在一个表中,这个要求有点高;其实这个问题是可以解决的,在系统不忙时完全可以从这个订单表中移走老的订单到另外一个表中,然后将这些订单的商品数从商品库存中扣减出来。有人会说这又回到老的方案中去了,我想说不然,这个处理完全是数据内部处理,完全不需要并发,也就不存在回到老的方案中的说法。