国产化信创改造:达梦/人大金仓适配与多数据库兼容方案实战(SpringBoot)
国产化信创改造:达梦/人大金仓适配与多数据库兼容方案实战(SpringBoot)
🌐演示地址:http://ruoyioffice.com | 📦源码1·GitHub:ruoyi-office | 📦源码2·GitCode:ruoyi-office | 📦源码3·Gitee:ruoyi-office | 💬微信:17156169080(备注「RuoYi Office」)
政企、国资、金融、医疗的项目越来越多地写明"国产化/信创要求":数据库必须用达梦、人大金仓、OpenGauss 等国产库,Oracle/MySQL 不再被接受。这时候原本跑在 MySQL 上的系统能不能"换个数据库就跑",就成了能不能接这个单子的硬门槛。本文基于 RuoYi Office 真实源码,讲清一套系统是怎么做到"一套代码、多库兼容"的,以及国产化改造中真实存在的坑和回归建议——不吹不黑。
▲ 信创多库全景:一套代码 → MyBatis-Plus 运行时识别方言 + 自研 DbTypeEnum + 主键策略自动适配 + 各库独立 DDL 脚本,覆盖达梦/人大金仓/OpenGauss 等国产库
引言:信创改造到底卡在哪?
国产化改造的难点不在"换驱动",而在"方言、主键、关键字处处不同"。几个典型痛点:
痛点一:主键策略不一样。MySQL 自增,Oracle/金仓要序列,达梦又是 IDENTITY——主键生成方式一换库就崩。
痛点二:SQL 方言不通用。FIND_IN_SET、LIMIT、分页、DUAL表在不同国产库写法不同。
痛点三:没有现成 DDL 脚本。MySQL 的建表语句直接拿到达梦上跑,类型和语法对不上。
痛点四:评估"到底支持哪些库"。宣传说"支持国产数据库",但真实适配到什么程度?需要心里有数。
| 现状 | 后果 |
|---|---|
| 主键写死自增 | 换序列库直接报错 |
| SQL 方言混用 | find_in_set 在 PG 系报错 |
| 无国产库 DDL | 建表失败 |
| 适配程度不明 | 投标/交付踩坑 |
方案一句话:MyBatis-Plus 运行时识别方言 + 自研 DbTypeEnum 增强 + 主键策略自动切换 + 各库独立 DDL 脚本,把"换库"成本降到最低。
一、实测支持哪些库:先把家底说清楚
先给一个诚实的支持分级,方便选型评估。"一等支持"指工程内有驱动、DDL 脚本、框架枚举、转换工具链:
| 级别 | 数据库 | 说明 |
|---|---|---|
| 一等(脚本+驱动+枚举+工具链) | MySQL、Oracle、PostgreSQL、SQL Server、达梦 DM8、人大金仓 KingbaseES、OpenGauss | 信创主力库均在列 |
| 二等(MySQL 协议兼容) | TiDB、MariaDB、OceanBase | 走 MySQL 驱动,无专属脚本 |
| 未适配 | IBM DB2 | 仓库自述暂未适配 |
国产库驱动坐标(按需引入,optional):
| 数据库 | 驱动坐标 | 版本 |
|---|---|---|
| 达梦 DM8 | com.dameng:DmJdbcDriver18 | 8.1.3.140 |
| 人大金仓 | cn.com.kingbase:kingbase8 | 9.0.1.jre7 |
| OpenGauss | org.opengauss:opengauss-jdbc | 7.0.0-RC3-og |
诚实说明:日常开发默认仍是 MySQL,国产库是"可切换"的一等公民,但生产交付前建议做模块级回归(原因见第四节)。
二、方言增强:自研 DbTypeEnum 抹平差异
MyBatis-Plus 能运行时从 JDBC 连接自动识别方言,框架再用自研DbTypeEnum对FIND_IN_SET等做逐库映射。这是"一套代码多库"的核心:
// DbTypeEnum:为每种库定义 find_in_set 的等价 SQL 模板MY_SQL(DbType.MYSQL,"MySQL","FIND_IN_SET('#{value}', #{column}) <> 0"),POSTGRE_SQL(DbType.POSTGRE_SQL,"PostgreSQL","POSITION('#{value}' IN #{column}) <> 0"),DM(DbType.DM,"DM DBMS","FIND_IN_SET('#{value}', #{column}) <> 0"),// 达梦:MySQL 风格KINGBASE_ES(DbType.KINGBASE_ES,"KingbaseES","POSITION('#{value}' IN #{column}) <> 0");// 金仓:PG 风格// 运行时按当前连接的产品名匹配publicstaticDbTypeEnumfind(StringdatabaseProductName){returnArrays.stream(values()).filter(e->e.getProductName().equals(databaseProductName)).findFirst().orElse(null);}设计要点:
- 达梦走 MySQL 风格(FIND_IN_SET),人大金仓走 PostgreSQL 风格(POSITION)——按各库的方言血缘归类。
- OpenGauss 不单独枚举:它的
DatabaseProductName与 PostgreSQL 相同,运行时自动走 PG 分支。 - 分页插件
PaginationInnerInterceptor不手动 setDbType,依赖 MyBatis-Plus 从连接自动识别,天然支持 DM/金仓等 MP 已知方言。
三、主键策略:换库自动切 AUTO / 序列
国产库主键差异最大,框架用IdTypeEnvironmentPostProcessor在启动时按库类型自动选主键策略。无需手改实体:
// IdTypeEnvironmentPostProcessor:启动时根据数据库类型自动设置 id-typeswitch(dbType){caseORACLE:casePOSTGRE_SQL:caseKINGBASE_ES:caseDB2:caseH2:setIdType(environment,IdType.INPUT);// 依赖序列 + @KeySequencebreak;caseMY_SQL:caseDM:default:setIdType(environment,IdType.AUTO);// MySQL 自增 / 达梦 IDENTITYbreak;}对需要序列的库,框架按库注册对应的IKeyGenerator:
| DbType | KeyGenerator |
|---|---|
| PostgreSQL | PostgreKeyGenerator |
| Oracle | OracleKeyGenerator |
| 人大金仓 KingbaseES | KingbaseKeyGenerator |
| 达梦 DM(INPUT 模式时) | DmKeyGenerator |
实体只需声明序列名,跨库通用:
// DO 上声明序列;MySQL/达梦 走 AUTO 时该注解不生效,PG/金仓走 INPUT 时启用@KeySequence("system_user_seq")// Oracle、PostgreSQL、Kingbase、DB2、H2 需要@TableName("system_users")publicclassAdminUserDOextendsTenantBaseDO{...}连 Quartz 定时任务的 JobStore 也按库切换委托:PostgreSQL →PostgreSQLDelegate,Oracle →OracleDelegate,达梦/金仓 → 标准StdJDBCDelegate。
▲ 基础设施·数据源配置:可管理多数据源、在线测试连接,切换国产库时配置 JDBC URL 即可,框架自动识别方言与主键策略
四、切库实操:到底要改什么
换数据库只需三步配置 + 导脚本,框架自动处理主键和方言。以切到达梦为例:
# application-dev.yaml:改 master 数据源 URL(驱动由 URL 推断)spring:datasource:dynamic:primary:masterdruid:validation-query:SELECT 1 FROM DUAL# Oracle/达梦/金仓/PG 通用datasource:master:url:jdbc:dm://127.0.0.1:5236?schema=RUOYI_VUE_PRO# 达梦username:SYSDBApassword:SYSDBA001mybatis-plus:global-config:db-config:id-type:NONE# 保持 NONE,由 PostProcessor 自动选 AUTO/INPUT配套动作:
| 步骤 | 动作 |
|---|---|
| 1 | 引入对应库 JDBC 驱动依赖(达梦DmJdbcDriver18) |
| 2 | 导入对应库 DDL:sql/dm/ruoyi-vue-pro-dm8.sql(金仓sql/kingbase/,OpenGausssql/opengauss/) |
| 3 | 改master数据源 URL/账号,id-type保持 NONE |
| 4 | 如需 MySQL→其他库转换,可用sql/tools/convertor.py dm8 |
▲ 基础设施·代码生成:从数据库读取表结构生成代码,多库环境下通过 JDBC Metadata 适配不同国产库的表/字段读取
诚实的缺口提示(信创改造务必心里有数):
- 部分业务 Mapper(商城促销、CRM、IoT 等)硬编码了
FIND_IN_SET,未统一走方言映射,切到 PostgreSQL/金仓可能需要逐个改写; - 代码生成器的菜单 SQL 模板未覆盖 OpenGauss 独立分支;
- 仓库无国产库集成测试用例。
所以正确的态度是:框架层一等支持 + 业务层模块回归。这正是真实信创项目该有的预期,而不是"换个 URL 就万事大吉"。
五、技术亮点总结
| 设计要点 | 实现方式 | 价值 |
|---|---|---|
| 方言识别 | MyBatis-Plus 运行时 + DbTypeEnum | 一套代码多库 |
| 主键自适配 | IdTypeEnvironmentPostProcessor | 换库不改实体 |
| 序列生成 | 按库注册 KeyGenerator | PG/金仓序列无感 |
| 独立 DDL | sql/dm、sql/kingbase、sql/opengauss | 建表开箱即用 |
| 转换工具 | convertor.py 多目标 | MySQL→国产库一键转 |
| 多数据源 | dynamic-datasource + Druid | 异构库共存 |
六、快速体验
- 在线演示:http://ruoyioffice.com/web/(账号
admin/admin123) - 操作路径:基础设施 → 数据源配置;源码
sql/目录下各库 DDL 脚本 - 推荐体验流程:查看数据源配置 → 看
sql/dm、sql/kingbase脚本 → 试用 convertor.py 转换
| 仓库 | 地址 |
|---|---|
| 后端 | GitHub · GitCode · Gitee |
| 前端 | GitCode |
延伸阅读:多数据源与读写分离实战 · SpringBoot 多租户 SaaS 架构。
常见问题(FAQ)
RuoYi Office 支持达梦、人大金仓吗?
支持,且是一等支持:有独立 DDL 脚本(sql/dm、sql/kingbase)、JDBC 驱动依赖、DbTypeEnum方言增强、主键策略自动适配(达梦 AUTO/金仓序列)、Quartz 委托切换。OpenGauss 同样有脚本与适配(运行时识别为 PostgreSQL)。
从 MySQL 切到国产库要改代码吗?
主体不用。改spring.datasource.dynamic.master的 URL/账号、引入对应驱动、导入对应库 DDL、id-type保持 NONE 即可,框架自动处理主键与方言。但需注意部分业务 Mapper 存在FIND_IN_SET硬编码,切 PostgreSQL 系(含金仓)可能要逐个改写,建议做模块回归。
主键在不同数据库怎么处理?
启动时IdTypeEnvironmentPostProcessor按库自动选策略:MySQL/达梦走 AUTO(自增/IDENTITY),Oracle/PostgreSQL/金仓走 INPUT + 序列(配合@KeySequence和对应 KeyGenerator)。
有没有 MySQL 转国产库的工具?
有。sql/tools/convertor.py支持把 MySQL DDL 转成 postgres/oracle/sqlserver/dm8/kingbase/opengauss 等目标库脚本。
信创改造能"换个 URL 就上线"吗?
不能盲目乐观。框架层对国产库是一等支持,但真实交付前建议做模块级回归(重点关注FIND_IN_SET、分页、代码生成等),这才是务实的信创落地态度。
💡想要体验 RuoYi Office 的强大功能?
🌐在线演示:http://ruoyioffice.com/web/(账号 admin / admin123)
📦源码仓库:GitHub | GitCode | Gitee
💬技术咨询:添加微信17156169080,备注「RuoYi Office」
⭐如果觉得不错,请给个 Star 支持一下!