赞
踩
说SpringBoot的多数据源配置之前,我们先了解下DataSource。
在java中,操作数据库有很多方式,在众多方式中除了JDBC外还有DataSource对象。
DataSource可以看作数据源:
它封装了数据库参数,连接数据库,程序中操作DataSource对象即可对数据库进行增删改查操作。
不同方式中使用的DataSource对象不同。列举如下:
- dbcp框架中的DataSource类是:org.apache.commons.dbcp.BasicDataSource
-
- c3p0框架的DataSource类是:com.mchange.v2.c3p0.ComboPooledDataSource
-
- MyBatis框架的DataSource类是:org.apache.ibatis.datasource.pooled.PooledDataSource
-
- Druid框架的DataSource类是:com.alibaba.druid.pool.DruidDataSource
对于DataSource的一些实现,经常被叫做数据库连接池,
比如Druid官方文档中说“Druid是Java语言中最好的数据库连接池“,本质核心就是DataSource的一个实现类,作为中间层使用,并且基本上都提供了附带的其他的服务,也就是说不仅仅实现了核心建筑,也基于核心之上构建了很多的外围建设。
·
学习JDBC的时候,直接使用DriverManager的这种形式,通常需要将驱动程序硬编码到项目中(JDBC4.0后可以自动注册驱动程序)。
而且最重要的是通过DriverManager的getConnection方法获取的连接,是建立与数据库的连接。
但是建立与数据库的连接是一项较耗资源的工作,频繁的进行数据库连接建立操作会产生较大的系统开销。
DataSource中获取的连接来自于连接池中,虽然池中的连接从根本上来说其实也还是从DriverManager获取而来。
DataSource就是DriverManager的一种替代角色,拥有对外提供连接的能力。
如果你新增的数据库数据源和目前的数据库不同,记得引入新数据库的驱动依赖,比如 MySQL 和 PGSQL。
- <dependency>
- <groupId>mysql</groupId>
- <artifactId>mysql-connector-java</artifactId>
- <scope>runtime</scope>
- </dependency>
-
- <dependency>
- <groupId>org.postgresql</groupId>
- <artifactId>postgresql</artifactId>
- <version>42.2.7</version>
- </dependency>
首先,需要在配置文件中配置多数据源的连接信息;
- spring:
- # 数据源配置
- datasource:
- ds1: #数据源1
- driver-class-name: com.mysql.jdbc.Driver # mysql的驱动你可以配置别的关系型数据库
- url: jdbc:mysql://ip:3306/db1 #数据源地址
- username: root # 用户名
- password: root # 密码
- ds2: # 数据源2
- driver-class-name: com.mysql.jdbc.Driver # mysql的驱动你可以配置别的关系型数据库
- url: jdbc:mysql://ip:3307/db2#数据源地址
- username: root # 用户名
- password: root # 密码
编写Springboot的配置类:
mybatis多数据源切换的原理是根据不同包,调用不同的数据源,
你只需要把你的mapper.java和mapper.xml 写在某个package中,springboot自动帮你实现数据源切换。
核心代码就这两句:
- @MapperScan(basePackages ="com.web.ds2.**.dao",
- sqlSessionTemplateRef = "ds2SqlSessionTemplate")
- sqlSessionFactory.
- setMapperLocations(new PathMatchingResourcePatternResolver().
- getResources("classpath*:com/web/ds2/**/*.xml"));
详细代码如下:
- /**
- * Mybatis主数据源ds1配置
- * 多数据源配置依赖数据源配置
- * @see DataSourceConfig
- */
- @Configuration
- @MapperScan(basePackages ="com.web.ds1.**.dao", sqlSessionTemplateRef = "ds1SqlSessionTemplate")
- public class MybatisPlusConfig4ds1 {
-
- @Bean(name = "dataSource1")
- @ConfigurationProperties(prefix = "spring.datasource.ds1")
- @Primary
- public DataSource dataSource() {
- return DataSourceBuilder.create().build();
- }
-
- //主数据源 ds1数据源
- @Primary
- @Bean("ds1SqlSessionFactory")
- public SqlSessionFactory ds1SqlSessionFactory(@Qualifier("ds1DataSource") DataSource dataSource) throws Exception {
- MybatisSqlSessionFactoryBean sqlSessionFactory = new MybatisSqlSessionFactoryBean();
- sqlSessionFactory.setDataSource(dataSource);
- sqlSessionFactory.setMapperLocations(new PathMatchingResourcePatternResolver().
- getResources("classpath*:com/web/ds1/**/*.xml"));
- return sqlSessionFactory.getObject();
- }
-
- @Primary
- @Bean(name = "ds1TransactionManager")
- public DataSourceTransactionManager ds1TransactionManager(@Qualifier("ds1DataSource") DataSource dataSource) {
- return new DataSourceTransactionManager(dataSource);
- }
-
- @Primary
- @Bean(name = "ds1SqlSessionTemplate")
- public SqlSessionTemplate ds1SqlSessionTemplate(@Qualifier("ds1SqlSessionFactory") SqlSessionFactory sqlSessionFactory) {
- return new SqlSessionTemplate(sqlSessionFactory);
- }
-
- }

- /**
- * Mybatis 第二个ds2数据源配置
- * 多数据源配置依赖数据源配置
- * @see DataSourceConfig
- */
- @Configuration
- @MapperScan(basePackages ="com.web.ds2.**.dao", sqlSessionTemplateRef = "ds2SqlSessionTemplate")
- public class MybatisPlusConfig4ds2 {
-
- @Bean(name = "dataSource2")
- @ConfigurationProperties(prefix = "spring.datasource.ds2")
- public DataSource dataSource() {
- return DataSourceBuilder.create().build();
- }
-
- //ds2数据源
- @Bean("ds2SqlSessionFactory")
- public SqlSessionFactory ds2SqlSessionFactory(@Qualifier("ds2DataSource") DataSource dataSource) throws Exception {
- MybatisSqlSessionFactoryBean sqlSessionFactory = new MybatisSqlSessionFactoryBean();
- sqlSessionFactory.setDataSource(dataSource);
- sqlSessionFactory.setMapperLocations(new PathMatchingResourcePatternResolver().
- getResources("classpath*:com/web/ds2/**/*.xml"));
- return sqlSessionFactory.getObject();
- }
-
- //事务支持
- @Bean(name = "ds2TransactionManager")
- public DataSourceTransactionManager ds2TransactionManager(@Qualifier("ds2DataSource") DataSource dataSource) {
- return new DataSourceTransactionManager(dataSource);
- }
-
- @Bean(name = "ds2SqlSessionTemplate")
- public SqlSessionTemplate ds2SqlSessionTemplate(@Qualifier("ds2SqlSessionFactory") SqlSessionFactory sqlSessionFactory) {
- return new SqlSessionTemplate(sqlSessionFactory);
- }
-
- }

@ConfigurationProperties(prefix = "spring.datasource.ds1"):使用spring.datasource.ds1开头的配置。
@Qualifier:指定数据源名称,与Bean中的name属性原理相同,主要是为了确保注入成功;
@Primary:声明这是一个主数据源(默认数据源),多数据源配置时必不可少。
@Primary :声明这是一个主数据源(默认数据源),多数据源配置时必不可少。@Qualifier:显式选择传入的 Bean。`
因为已经在两个数据源中分别配置了扫描的 Mapper 路径,如果你之前在 SpringBoot 启动类中也使用了 Mapper 扫描注解,需要删掉。
Service层:
- @Service
- public class TestService {
-
- @Resource
- private ClusterMapper clusterMapper;
- @Resource
- private MasterMapper masterMapper;
-
- public List<HashMap<String, Object>> queryBooks() {
- return masterMapper.queryBooks(); //指定的配置类扫描的是一个包
- }
-
- public List<HashMap<String, Object>> queryOrders() {
- return clusterMapper.queryOrders(); //指定的配置类扫描的是另一个包
- }
- }

Controller层:
- @RestController
- @RequestMapping(value = "/test", method = RequestMethod.POST)
- public class TestController {
- @Resource
- private TestService testService;
-
- @RequestMapping("/books")
- public List<HashMap<String, Object>> queryBooks() {
- return testService.queryBooks();
- }
-
- @RequestMapping("/orders")
- public List<HashMap<String, Object>> queryOrders() {
- return testService.queryOrders();
- }
- }

其实在多数据源改造中,我们一般情况下都不会使用默认的 JDBC 连接方式,往往都需要引入连接池进行连接优化,不然你可能会经常遇到数据源连接被断开等报错日志。
其实数据源切换连接池数据源也是十分简单的,直接引入连接池依赖,然后把创建 dataSource 的部分换成连接池数据源创建即可。
下面以阿里的 Druid 为例,先引入连接池数据源依赖。
- <dependency>
- <groupId>com.alibaba</groupId>
- <artifactId>druid</artifactId>
- </dependency>
配置文件中,添加 Druid 的一些配置。
- spring.datasource.datasource2.initialSize=3 # 根据自己情况设置
- spring.datasource.datasource2.minIdle=3
- spring.datasource.datasource2.maxActive=20
改写 dataSource 这个Bean 的创建代码部分:
- /**
- * Mybatis 第二个ds2数据源配置
- * 多数据源配置依赖数据源配置
- * @see DataSourceConfig
- */
- @Configuration
- @MapperScan(basePackages ="com.web.ds2.**.dao", sqlSessionTemplateRef = "ds2SqlSessionTemplate")
- public class MybatisPlusConfig4ds2 {
-
- @Value("${spring.datasource.datasource2.jdbc-url}")
- private String url;
- @Value("${spring.datasource.datasource2.driver-class-name}")
- private String driverClassName;
- @Value("${spring.datasource.datasource2.username}")
- private String username;
- @Value("${spring.datasource.datasource2.password}")
- private String password;
- @Value("${spring.datasource.datasource2.initialSize}")
- private int initialSize;
- @Value("${spring.datasource.datasource2.minIdle}")
- private int minIdle;
- @Value("${spring.datasource.datasource2.maxActive}")
- private int maxActive;
-
- @Bean(name = "dataSource2")
- public DataSource dataSource() {
- DruidDataSource dataSource = new DruidDataSource();
- dataSource.setUrl(url);
- dataSource.setDriverClassName(driverClassName);
- dataSource.setUsername(username);
- dataSource.setPassword(password);
- dataSource.setInitialSize(initialSize);
- dataSource.setMinIdle(minIdle);
- dataSource.setMaxActive(maxActive);
- return dataSource;
- }
-
- //...
-
- }

Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。