文章目录
-
-
- 前言
- 一、数据同步方案
-
-
1.同步双写
- [2.异步双写(MQ方式)](#2MQhttpssocsdnnetsosearchqMQspm1001210130017020_53)
- 3.基于Mysql表定时扫描同步
- [4.基于Binlog实时同步](#4BinloghttpssocsdnnetsosearchqBinlogspm1001210130017020_119)
-
1.同步双写
- [二、数据迁移同步工具选型](#httpssocsdnnetsosearchqspm1001210130017020_141)
-
- 总结
-
前言
我们一般会使用Mysql用来存储数据,用Es来做全文检索和特殊查询,用redis来做数据的缓存
那么如何将数据优雅的从Mysql同步到Es以及redis呢?
一、数据同步方案
1.同步双写
这是一种最为简单的方式,在将数据写到mysql时,同时将数据写到ES或者redis。
这个方法的缺点是代码严重耦合,需要手动维护Mysql和Es数据关系,非常不便于维护。
伪代码:
/\*\*
\* 新增商品
\*/
@Transactional(rollbackFor = Exception.class)
public void addGoods(GoodsDto goodsDto) {
//1、保存Mysql
Goods goods = new Goods();
BeanUtils.copyProperties(goodsDto,goods);
goodsMapper.insert();
//2、保存ES
IndexRequest indexRequest = new IndexRequest("goods\_index","\_doc");
indexRequest.source(JSON.toJSONString(goods), XContentType.JSON);
indexRequest.setRefreshPolicy(WriteRequest.RefreshPolicy.IMMEDIATE);
highLevelClient.index(indexRequest);
}
- 优点:
1、业务逻辑简单
2、实时性高 - 缺点:
1、 硬编码,有需要写入mysql的地方都需要添加写入ES的代码;
2、 业务强耦合;
3、 存在双写失败丢数据风险;
4、 性能较差:本来mysql的性能不是很高,再加一个ES,系统的性能必然会下降。 - 双写失败风险,包括以下几种:
1) ES系统不可用;
2) 程序和ES之间的网络故障;
3) 程序重启,导致系统来不及写入ES等。
针对这种情况,有数据强一致性要求的,就必须双写放到事务中来处理,而一旦用上事物,则性能下降更加明显。
2.异步双写(MQ方式)
针对多数据源写入的场景,可以借助MQ实现异步的多源写入,这种情况下各个源的写入逻辑互不干扰,不会由于单个数据源写入异常或缓慢影响其他数据源的写入,虽然整体写入的吞吐量增大了,但是由于MQ消费是异步消费,所以不适合实时业务场景。
在执行完向Mysql中写入数据的逻辑后,发送MQ,告诉消费端这个数据需要写入Es,消费端收到消息后执行向Es写入数据的逻辑。这个方式的优点是Mysql和Es数据维护分离,开发Mysql和Es的人员只需要关心各自的业务。缺点是依然需要维护发送、接收MQ的逻辑,并且引入了MQ组件,增加了系统的复杂度。
伪代码:
@Transactional(rollbackFor = Exception.class)
public boolean parseJdDb(String keyword) throws IOException {
//向数据库中插入
List<JdGoods> jdGoods = htmlParseUtil.parseJd(keyword);
//批量更新Mysql
boolean b = this.saveBatch(jdGoods);
log.info("异步同步至ES");
rabbitTemplate.convertAndSend("es.exchange","es.renew.key", jdGoods);
return b;
}
优点:
1、性能高
2、不易出现数据丢失问题,主要基于MQ消息的消费保障机制,比如ES宕机或者写入失败,还能重新消费MQ消息。
3、多源写入之间相互隔离,便于扩展更多的数据源写入
缺点:
1、硬编码问题,接入新的数据源需要实现新的消费者代码
3、系统复杂度增加:引入了消息中间件
4、可能出现延时问题:MQ是异步消费模型,用户写入的数据不一定可以马上看到,造成延时。
3.基于Mysql表定时扫描同步
上面两种方案中都存在硬编码问题,也就是有任何对mysq进行增删改查的地方要么植入ES代码,要么替换为MQ代码,代码的侵入性太强。
如果对实时性要求不高的情况下,可以考虑用定时器来处理,具体步骤如下:
1、数据库的相关表中增加一个字段为timestamp的字段,任何crud操作都会导致该字段的时间发生变化;
2、原来程序中的CURD操作不做任何变化;
3、增加一个定时器程序,让该程序按一定的时间周期扫描指定的表,把该时间段内发生变化的数据提取出来;
4、逐条写入到ES中。
如下图所示:
该方案的典型实现是借助logstash
实现数据同步,其底层实现原理就是根据配置定期使用sql查询新增的数据写入ES中,实现数据的增量同步。
具体实现可以参考:通过Logstash实现mysql数据定时增量同步到ES
优点:
1、不改变原来代码,没有侵入性、没有硬编码;
2、没有业务强耦合,不改变原来程序的性能;
3、Worker代码编写简单不需要考虑增删改查;
缺点:
1、时效性较差,由于是采用定时器根据固定频率查询表来同步数据,尽管将同步周期设置到秒级,也还是会存在一定时间的延迟。
2、对数据库有一定的轮询压力,一种改进方法是将轮询放到压力不大的从库上。
业界目前较为流行的方案:Canal实现Mysql数据同步至Redis、Elasticsearch
4.基于Binlog实时同步
自我介绍一下,小编13年上海交大毕业,曾经在小公司待过,也去过华为、OPPO等大厂,18年进入阿里一直到现在。
深知大多数大数据工程师,想要提升技能,往往是自己摸索成长或者是报班学习,但对于培训机构动则几千的学费,着实压力不小。自己不成体系的自学效果低效又漫长,而且极易碰到天花板技术停滞不前!
因此收集整理了一份《2024年大数据全套学习资料》,初衷也很简单,就是希望能够帮助到想自学提升又不知道该从何学起的朋友。
既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,基本涵盖了95%以上大数据开发知识点,真正体系化!
由于文件比较大,这里只是将部分目录大纲截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且后续会持续更新文章来源:https://www.toymoban.com/news/detail-856407.html
如果你觉得这些内容对你有帮助,可以添加VX:vip204888 (备注大数据获取)
开发知识点,真正体系化!**
由于文件比较大,这里只是将部分目录大纲截图出来,每个节点里面都包含大厂面经、学习笔记、源码讲义、实战项目、讲解视频,并且后续会持续更新
如果你觉得这些内容对你有帮助,可以添加VX:vip204888 (备注大数据获取)
[外链图片转存中…(img-0htuFViP-1712853349909)]文章来源地址https://www.toymoban.com/news/detail-856407.html
到了这里,关于Mysql和ES、Redis数据同步方案汇总_redis同步数据从mysql到es的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!