数据库 跨库查询

287 阅读2分钟

背景

微服务的情况下,数据库也是微服务的,即不是一个单体库,而是多个库。

怎么办,怎么查询?

分类

这里面其实是分了不同的情况的。

比如说,分表分库的时候,选择哪个字段来分库。这是一个维度,即拆分字段的维度。然后,查询的时候,根据是否是拆分字段,其实解决方法是不一样的。


分类

拆分字段

1.单个值
2.多个值

拆分字段,可以基于hash,唯一定位到是哪个库。

非拆分字段

1.冗余数据
冗余字段

2.组合数据
先分开独立查,然后把各个库的是组合到一起,得到最终的数据

3.复制数据
引入中间件ETL。冗余整个表。就是把相关的多个表的数据,全部复制到一个库,从而解决跨库问题,即避免跨库查询,只在一个备份库查询。

拆分字段

单个值

sql

select *
from order
where userid='XXX'

解决方法 是hash。就是基于userid的value去hash,取模。计算出来的,就是唯一定位是哪个库。即写的时候和读的时候,是同一个库。

多个值

sql

select *
from order
where userid in (value1,value2,value3)

解决方法
1.只能先查各自库的数据,就是分开查
2.然后,组合数据

具体操作的时候,就是每个value都hash,找到对应的数据库。最终,组合各个库的数据,在程序代码层面。

非拆分字段

冗余数据

sql

select *
from order
where name='XXX' //name字段在user表

解决方法
order表冗余存储name字段。


数据一致性
name变了,怎么办?
1.方法1
数据库的触发器

2.方法2
代码层面,同时更新冗余字段的数据。


应用场景
只适合依赖字段比较少的情况。如果更多,就不适合。


实现思路
以空间换时间。

组合数据

在程序层面,多次查询,然后组合各个库的数据。

复制数据

本质是把数据弄到一个库去。具体解决方法是引入中间件ETL。复制相关的表,到一个备用库去。

总结

实际上,具体用的时候,其实需要跨库查询的时候,并不是很多。

一般有的话,也是那种频繁查询的数据,还有量比较大的数据。才偶尔需要跨库查询一下。大部分时候,是不需要做跨库查询的。

参考

mp.weixin.qq.com/s/r2t4P3A7C…
mp.weixin.qq.com/s/9G-_U6di0…
mp.weixin.qq.com/s/9fBx2bSWX…