mysql 和 es 的一致性方案,你知道几个呢?
- 如何保证 Mysql 和 es 数据一致性问题及方案?
- 如果保证 Mysql 和 redis 数据一致性问题及方案?
- 如果保证 Mysql 和 HBase 数据一致性?
- 等等等等?
- 把商品数据冗余存储在Elasticsearch中,实现高速搜索
- 把商品数据冗余存储在redis 中,实现高速缓存
很多时候,要求保持很高的数据一致性
- 要求 mysql 与 es 做到秒级别的数据同步。
- 要求 mysql 与 redis 做到秒级别的数据同步。
那要如何做呢?
方案一:同步双写
同步双写是一种最为简单的方式,在将数据写到 MySQL 时,同时将数据写到 ES
优点:简单粗暴,实时写入能做到秒级。
缺点:
- 业务耦合,这种方式代码侵入性强,商品的管理中耦合大量数据同步代码,要在之前写 mysql 的地方加写 es 的代码。以后写 mysql 的地方也要加写 es 的代码。
- 影响性能,写入两个存储,响应时间变长,本来 MySQL 的性能不是很高,再加一个 ES,系统的性能必然会下降。
- 不便扩展:搜索可能有一些个性化需求,需要对数据进行聚合,这种方式不便实现
- 高风险:存在双写失败丢数据风险
方案二:异步双写
同步操作性能低,异步性能高
异步双写分两种:
- 使用内存队列(如阻塞队列)异步
- 使用消息队列进行异步
使用内存队列(如阻塞队列)异步:
先把商品数据写入DB后,然后把 数据写入 BlockingQueue 阻塞队列,消费线程异步从 drain 数据,batch 写入 ElasticSearch,保证数据一致性
使用消息队列进行异步:
异步双写优点:
- 性能高;
- 不易出现数据丢失问题,主要基于 MQ 消息的消费保障机制,比如 ES 宕机或者写入失败,还能重新消费 MQ 消息;
- 多源写入之间相互隔离,便于扩展更多的数据源写入。
异步双写缺点:
- 硬编码问题,接入新的数据源需要实现新的消费者代码;
- 系统复杂度增加,引入了消息中间件;
- MQ是异步消费模型,用户写入的数据不一定可以马上看到,造成延时。
方案三:定期同步
为了保证 DB和ES数据一致性,包括两个方面
- 增量数据一致性
- 全量数据一致性
优点:
实现比较简单
缺点:
- 实时性难以保证
- 对存储压力较大
方案四:数据订阅
如果要提高实时性,又要低入侵, 可以利用 MySQL 的 Binlog 来进行同步
MySQL通过binlog订阅实现主从同步,canal Server 是一个伪装的slave节点,接收到binlog日志后,发送到MQ, 其他的 存储消费 MQ里边 的binlog日志,实现数据订阅。
这种方式和异步双写比较像,但是有两个优点:
- 第一降低了商品服务的入侵性
- 第二数据的实时性更好
数据订阅框架的选型,主流的大体上是有:Canal、Maxwell、Python-Mysql-Rplication
具体的操作可以私下查阅
方案五:elt工具
MySQL同步到Redis、MySQL同步到hbase、MySQL同步到es、或机房同步、主从同步等,都可以考虑使用elt工具
什么是elt工具?
ETL,是英文 Extract-Transform-Load 的缩写,用来描述将数据从来源端经过抽取(extract)、转换(transform)、加载(load)至目的端的过程。ETL一词较常用在数据仓库,但其对象并不限于数据仓库。
ETL是构建数据仓库的重要一环,用户从数据源抽取出所需的数据,经过数据清洗,最终按照预先定义好的数据仓库模型,将数据加载到数据仓库中去。
常用的etl工具有: databus、canal (方案四用了这个组件,有etl 的部分功能)、otter 、kettle 等