canal数据同步方案设计
背景:
项目中一部分数据如页面静态数据需要从redis中获取,以提高页面加载速度。页面数据的修改是通过管理画面修改mysql,通过定时任务或手动将mysql数据同步到redis,以供页面获取。这里数据同步不是增量同步,而是根据条件查询得到数据集后同步。网关中的一些参数同样是在mysql维护,然后定时或手动推送到redis,并通知网关刷新内存数据。有时增加一个数据的变动会出发多个同步操作,如增加一个api,既要将其在门户画面展示,又要推送到网关,如果想实时生效就需要两次手动操作。这样就很繁琐,因此设计一种实时或准实时将mysql同步至redis的方案。
方案1:
更新数据库的同时执行同步redis方法,如在增删改首页数据的方法添加注解,利用aop统一处理数据同步的逻辑。这种方案实际就是spring cache。但是这里不仅仅要将数据同步至redis,还要发布订阅事件,因此需要自己实现aop逻辑。
方案2:
利用canal,监听mysql数据变更进行数据同步和发布订阅事件。这样不必修改原代码,逻辑解耦。并且如果mysql修改失败不会触发同步操作。
综上采用方案2。
详细方案设计:
在canal定义一个destination监听数据库,当有感兴趣的数据变动时,通过feign调用对应服务的同步方法(这里的同步方法复用已有的手动调用方法,不用新写)。因为同步的是准全量数据,为避免mysql每次更新都查询,党一个数据变动后一分钟内没有新的数据变动,才触发同步操作。此外,通过apollo配置中心动态启停同步服务。
canal部署:
参照官网的方案,利用zookeeper进行服务协调,实现canal server,canal client的高可用。
由于测试环境分为SIT,QA和UAT,每个环境有单独的数据库,因此canal定义三个destination监听对应的数据库实例。
未来的优化方向:
Redis获取数据失败fallback到数据库
增加一层内存缓存
感知同步数据成功与否
作者:ssd
链接:https://juejin.cn/post/6881578926771666951
来源:稀土掘金
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。