如何基于REST API查询参数加载不同配置文件实现多数据源导入导出
实现动态多数据源导入导出的方案
你之前的方案失效的核心原因是:你使用的@Value注解+单例@Component配置类是Spring容器启动阶段就完成属性注入的,属性值是固定写死的,无法根据运行时请求携带的source参数动态切换,所以即使做多配置文件也没法生效。
以下是可落地的松耦合实现方案:
实现步骤
1. 调整配置文件结构,按source分组存储所有数据源配置
把所有数据库配置统一放到application.yml或application.properties中,用source参数值作为分组key,后续新增数据源仅需要加配置,不需要修改业务代码:
database: config: # key对应接口的source参数值,比如oracle、mariadb oracle: url: jdbc:oracle:thin:@//xxx:1521/orcl username: oracle_user password: oracle_pwd driver-class-name: oracle.jdbc.OracleDriver mariadb: url: jdbc:mariadb://xxx:3306/test_db username: mariadb_user password: mariadb_pwd driver-class-name: org.mariadb.jdbc.Driver
2. 批量加载所有数据源配置
用@ConfigurationProperties批量加载所有配置到Map中,避免逐个写@Value注入:
@ConfigurationProperties(prefix = "database.config") @Component public class DatasourceProperties { // key是source参数值,value是对应数据源的配置信息 private Map<String, DatasourceInfo> configs = new HashMap<>(); public static class DatasourceInfo { private String url; private String username; private String password; private String driverClassName; // 此处省略getter、setter } // 此处省略configs的getter、setter }
3. 封装动态数据源持有类,加缓存优化性能
动态创建数据源,同时做本地缓存避免每次请求都重建连接池:
@Component public class DynamicDatasourceHolder { @Autowired private DatasourceProperties datasourceProperties; // 缓存已创建的数据源,key为source标识 private final Map<String, DataSource> datasourceCache = new ConcurrentHashMap<>(); public DataSource getDatasource(String source) { // 命中缓存直接返回 if (datasourceCache.containsKey(source)) { return datasourceCache.get(source); } // 读取对应source的配置 DatasourceProperties.DatasourceInfo info = datasourceProperties.getConfigs().get(source); if (info == null) { throw new IllegalArgumentException("不支持的数据源类型:" + source); } // 新建数据源,此处以Hikari连接池为例,可替换为你自己的数据源实现 HikariDataSource datasource = new HikariDataSource(); datasource.setJdbcUrl(info.getUrl()); datasource.setUsername(info.getUsername()); datasource.setPassword(info.getPassword()); datasource.setDriverClassName(info.getDriverClassName()); // 可自行补充其他连接池配置 datasourceCache.put(source, datasource); return datasource; } }
4. 改造导入导出接口,动态获取数据源
直接在接口层根据请求参数获取对应数据源,兼容你原有业务逻辑:
@RestController public class DataTransferController { @Autowired private DynamicDatasourceHolder datasourceHolder; @GetMapping("/export") public void export(@RequestParam String source) { DataSource exportDatasource = datasourceHolder.getDatasource(source); // 复用你原有导出逻辑即可 } @GetMapping("/import") public void importData(@RequestParam String source) { DataSource importDatasource = datasourceHolder.getDatasource(source); // 复用你原有导入逻辑即可 } }
松耦合优势
- 符合开闭原则:新增数据源仅需要在配置文件加对应配置,不需要修改任何业务代码
- 配置与逻辑完全分离:没有把数据源配置硬编码在Java类中,调整配置不需要重启服务(搭配Spring Cloud Config等配置中心可实现热更新)
- 导入导出逻辑复用同一套数据源获取能力,不需要分别维护导入、导出两套配置类,减少代码冗余
内容的提问来源于stack exchange,提问作者nee nee
相关产品推荐
相关产品推荐

