一、背景
最近,在版本封板的前夕,测试小姐姐突然找来,说有个功能设置了发送结果推送,设置的总共推送次数是99次,但是推送记录却有150多条,很显然数据出现了多发。
二、问题初修复
发送结果推送,在Web中由单独一条线程进行处理的。消息下发的时候,会先将推送数据记录到数据库的一个表中,同时投递到一个消息到延迟队列进行消费,通知线程会判断消息是否下发成功,成功则会进行通知,如果是还没下发或者待审核状态则重新投递回队列。另外模块初始化的时候也会去数据库里加载任务投递到队列里执行。
阅读代码发现,通知线程是没有加节点锁,意味着如果当前数据库中存在需要执行的任务,此时模块多节点重启,就会同时去加载任务并执行,从而造成数据下发。问题看起来不难解决,Web模块本身就有基于Redisson实现的节点锁,给任务加上一个就可以解决(恩,我真是个机灵鬼)。
基于Redisson实现的节点锁:
public class RedisDistributedLock {
private static