上次曾和大家说过DDL-脏数据层的实现,当时的我以为使用它的最大好处就是减少IO操作。但最近在项目中使用时,发现它也可以作为事务的一种临时实现。
大家知道,在Mongodb4.0之前是不支持事务的。因此,如果你的MongoDB使用的是低于4.0的版本,那么你一般都是在业务层去弥补,而这个DDL也可以做这样的事。
DDL中,业务场景一般是一个请求过来,直接修改缓存中的数据,我们默认这一步是成功的。后台会有一个专门的线程去定期扫描所有的脏数据,如果脏数据有脏字段
,那么就将脏数据入库,入库成功自然便是皆大欢喜了,但如果不成功呢?
记得当时用MySql数据库,项目用的Spring boot + MyBatis,利用@Transactional
注解,将几个数据库操作放在一个方法,这样即便出错,也可以自动回退。
但现在我们用的是MongoDB,而且我现在的版本是3.2(坑爹的阿里云服务)。数据库本身就不支持事务,这样我的DDL在将脏数据刷入数据库时,如果抛错,那么我的缓存里依旧是正确的数据,我只需要继续记录这些没有成功刷入数据库的脏数据字段,那么缓存里的数据,就依旧是刷入数据库之前的状态。而当后续请求进来后,其访问到的,也还是缓存里的正确数据。你只需要在抛错处设置报警,这样就可以即时知道问题,此时只需要专心修改这些问题,这样脏数据就会在线程下一次运行中,将数据刷入数据库中。