本文目录导读:

合并多个数据库的查询结果通常有多种场景,取决于数据库技术栈(SQL、NoSQL)以及数据是否需要去重、关联或聚合。
以下从最常见的技术场景出发,给出具体的合并方案:
合并多个同构表(结构相同的数据)
这是最简单的场景,比如从全国多个分库(上海库、北京库)查询用户表,然后合并。
SQL中的 UNION / UNION ALL
UNION:合并结果集并自动去重(会消耗更多性能)。UNION ALL:合并结果集,保留所有行(速度更快,通常推荐)。SELECT name, age FROM shanghai_users UNION ALL SELECT name, age FROM beijing_users;
Python(pandas)—— 适合数据分析、本地合并
import pandas as pd
import sqlalchemy
# 分别查询
df_sh = pd.read_sql('SELECT name, age FROM users', engine_shanghai)
df_bj = pd.read_sql('SELECT name, age FROM users', engine_beijing)
# 纵向拼接(类似 UNION ALL)
df_all = pd.concat([df_sh, df_bj], ignore_index=True)
# 如果需要去重(类似 UNION)
df_all = df_all.drop_duplicates()
数据库联邦引擎
- SQL Server 的 Linked Server:创建链接服务器,然后用
OPENQUERY合并。 - Oracle Database Link:通过
DBLINK直接跨库查询。 - MySQL FEDERATED 引擎:创建本地虚拟表映射到远程表。
合并多个异构数据库(不同品牌/不同表结构)
从 MySQL 取订单,从 PostgreSQL 取用户,从 MongoDB 取商品信息,最终合成一张报表。
使用 ETL 工具(推荐生产环境)
- Apache NiFi, Talend, Kettle:可视化设计合并流程。
- dbt:通过 SQL 跨平台查询(需要中间仓库)。
- Airbyte / Fivetran:专门用于数据同步。
编程脚本(灵活、快速)
# 从MySQL获取订单
import psycopg2
import pymongo
orders = query_mysql("SELECT user_id, amount FROM orders")
users = query_postgres("SELECT id, name FROM users")
products = query_mongodb("products", {})
# 使用pandas进行横向合并(按key匹配)
import pandas as pd
df_orders = pd.DataFrame(orders)
df_users = pd.DataFrame(users)
df_result = df_orders.merge(df_users, left_on='user_id', right_on='id', how='left')
Presto / Trino(SQL联邦查询引擎)
这是最优雅的跨库方案,配置好数据源(Connector)后,用 SQL 直接合并:
-- 假设配置了 mysql_catalog、postgres_catalog、mongo_catalog
SELECT
o.order_id,
u.name,
p.title
FROM mysql_catalog.sales.orders o
LEFT JOIN postgres_catalog.public.users u ON o.user_id = u.id
LEFT JOIN mongo_catalog.inventory.products p ON o.product_id = p._id;
合并时需要考虑的关键问题
| 问题 | 解决方案 |
|---|---|
| 字段不一致 | 使用 AS 别名统一字段名;或编程脚本中显式重命名。 |
| 数据类型冲突 | 统一转换成通用类型(尽量用字符串或数字)。 |
| 时区/编码 | 在查询时就用 CONVERT_TZ 或 ENCODE 统一(如统一转成 UTC)。 |
| 性能、大表合并 | 优先使用数据库内 UNION 或中间层数据仓库;避免脚本全量拉取。 |
| 去重逻辑 | 明确业务需求:按主键去重?按业务规则(如取最新记录)去重? |
| 事务一致性 | 跨库无法保证 ACID,推荐最终一致性策略,或使用两阶段提交框架(如 Seata、Saga)。 |
两张图总结
场景1:同构表(相同结构) DB1 (users) → UNION / pandas concat → 合并结果 DB2 (users) → 场景2:异构表(不同结构/不同品牌) MySQL (orders) ┐ PostgreSQL (users) ── Presto / 编程脚本 merge ── 最终报表 MongoDB (products) ┘
建议(按需求选择)
| 你的情况 | 推荐做法 |
|---|---|
| 只是临时查几个表,结构相同 | 直接用 UNION ALL |
| 多个数据库类型不同,需要实时查询 | 安装 Presto / Trino |
| 需要定期做报表,数据量大 | 用 ETL 工具(如 Airflow + dbt) |
| 开发一个简单的接口或脚本 | 用 Python + pandas / polars |
| 数据量极大(数十亿行) | 迁移到 数据仓库(ClickHouse、Redshift、Snowflake) 用 T+1 汇总 |
如果你能补充更多信息(例如数据库类型、数据量级、合并频率、是否实时),我可以给出更具体的代码或架构方案。