Springboot 多数据源配置,结合tk-mybatis
一、前言
作为一个资深的CRUD工程师,我们在实际使用springboot开发项目的时候,难免会遇到同时使用多个数据库的情况,比如前脚刚查询mysql,后脚就要查询sqlserver。
这时,我们很直观的就会想到,为springboot配置多个数据源,需要用哪个数据库连接,直接@Autowired不就行了。那么问题来了,怎么配置呢?
********************************************************************************************************************************************************************
退后,我要开始装逼了
********************************************************************************************************************************************************************
二、前期工作
1.数据库。
这里我准备了一个mysql数据库和一个sqlserver数据库。
Mysql脚本:
DROP TABLE IF EXISTS `tb_user`;
CREATE TABLE `tb_user` (
`id` int(8) NOT NULL,
`name` varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL,
PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8mb4 COLLATE = utf8mb4_general_ci ROW_FORMAT = Dynamic; -- ----------------------------
-- Records of tb_user
-- ----------------------------
INSERT INTO `tb_user` VALUES (0, '张三');
INSERT INTO `tb_user` VALUES (1, '李四');
INSERT INTO `tb_user` VALUES (2, '王五');
INSERT INTO `tb_user` VALUES (3, '赵六'); SET FOREIGN_KEY_CHECKS = 1;
sqlserver脚本:
IF EXISTS (SELECT * FROM sys.all_objects WHERE object_id = OBJECT_ID(N'[dbo].[test]') AND type IN ('U'))
DROP TABLE [dbo].[test]
GO CREATE TABLE [dbo].[test] (
[id] int NOT NULL,
[career] varchar(255) COLLATE Chinese_PRC_90_CI_AS NULL
)
GO ALTER TABLE [dbo].[test] SET (LOCK_ESCALATION = TABLE)
GO -- ----------------------------
-- Records of test
-- ----------------------------
INSERT INTO [dbo].[test] ([id], [career]) VALUES (N'1', N'软件工程师')
GO INSERT INTO [dbo].[test] ([id], [career]) VALUES (N'2', N'硬件工程师')
GO INSERT INTO [dbo].[test] ([id], [career]) VALUES (N'3', N'理财顾问')
GO INSERT INTO [dbo].[test] ([id], [career]) VALUES (N'4', N'律师')
GO INSERT INTO [dbo].[test] ([id], [career]) VALUES (N'5', N'数学家')
GO -- ----------------------------
-- Primary Key structure for table test
-- ----------------------------
ALTER TABLE [dbo].[test] ADD CONSTRAINT [PK__test__3213E83F1910436D] PRIMARY KEY CLUSTERED ([id])
WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON)
ON [PRIMARY]
GO
2.项目依赖。
springboot版本:2.0.6.RELEASE
依赖这里就不贴出来了,都是常见的几个starter而已。
tk.mybatis插件
这里我着重说一下tk.mybatis插件的配置。因为我们要使用该插件自动生成mapper等相关文件,但是我们又使用了两个不同的数据库,因此,需要对该插件分别作不同的参数配置,然后分别自动生成。
注意不要同时配置插件,不然会插件引入冲突。
关于如何使用tk.mybatis插件,请移步 使用mybatis-generator插件结合tk.mybatis自动生成mapper二三事
<!-- mysql 数据库 -->
<!--<plugin>
<groupId>org.mybatis.generator</groupId>
<artifactId>mybatis-generator-maven-plugin</artifactId>
<version>1.3.5</version>
<configuration>
<configurationFile>src/main/resources/generator/generatorConfig-mysql.xml</configurationFile>
<overwrite>true</overwrite>
<verbose>true</verbose>
</configuration>
<dependencies>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>${mysql.version}</version>
</dependency>
<dependency>
<groupId>tk.mybatis</groupId>
<artifactId>mapper</artifactId>
<version>3.4.4</version>
</dependency>
</dependencies>
</plugin>-->
<!-- sqlserver 数据库 -->
<plugin>
<groupId>org.mybatis.generator</groupId>
<artifactId>mybatis-generator-maven-plugin</artifactId>
<version>1.3.5</version>
<configuration>
<configurationFile>src/main/resources/generator/generatorConfig-sqlserver.xml</configurationFile>
<overwrite>true</overwrite>
<verbose>true</verbose>
</configuration>
<dependencies>
<dependency>
<groupId>com.microsoft.sqlserver</groupId>
<artifactId>sqljdbc4</artifactId>
<version>${sqlserver.sqljdbc4.version}</version>
</dependency>
<dependency>
<groupId>tk.mybatis</groupId>
<artifactId>mapper</artifactId>
<version>3.4.4</version>
</dependency>
</dependencies>
</plugin>
三、重头戏
1.spring配置文件
我们知道在application.yml(properties)文件中,可以配置一个数据源,spring在启动时,会自动加载该配置,并实例化数据库连接:
spring:
datasource:
type: com.zaxxer.hikari.HikariDataSource
url: jdbc:mysql://192.168.139.129:3306/demo?useUnicode=true&characterEncoding=utf-8&useSSL=false
username: root
password: root
driver-class-name: com.mysql.jdbc.Driver
hikari:
minimum-idle: 1
maximum-pool-size: 20
但是我们现在有多个数据源怎么办呢?难道直接粗暴的写两个?spring能自动识别两个数据源配置么?
这时,我们就需要手动使用@Bean的方式在代码中进行不同数据源的实例化配置了。为了更方便的管理配置信息,所以,我们仍然将配置信息写在application.yml中便于属性自动注入,但同时,对每一组数据源配置信息,需要加上前缀用以区分。
spring:
datasource:
test-mysql:
type: com.zaxxer.hikari.HikariDataSource
url: jdbc:mysql://192.168.139.129:3306/demo?useUnicode=true&characterEncoding=utf-8&useSSL=false
username: root
password: root
driver-class-name: com.mysql.jdbc.Driver
hikari:
minimum-idle: 1
maximum-pool-size: 20 test-sqlserver:
type: com.zaxxer.hikari.HikariDataSource
url: jdbc:sqlserver://192.168.139.129;DatabaseName=dbo
username: sa
password: qwe!@#123
driver-class-name: com.microsoft.sqlserver.jdbc.SQLServerDriver
hikari:
minimum-idle: 1
maximum-pool-size: 20
2.手动配置数据源
通过手动配置数据源,分别实例化不同的数据源连接对象,以实现spring的多数据源配置。由于多个数据源对于spring来说都是DataSource及其相关类型的Bean,那么在spring容器进行DataSource实例化注入容器的时候,就会很困惑:WDNMD,你给劳资搞了几个数据源啊?这么多“妹子”,我先“嘿咻”谁?所以,为了让spring能够顺利的实例化我们配置的所有DataSource,就需要我们手动指定优先级,使用@Primary注解告知spring当前Bean的优先级更高。
主数据源(mysql)
package com.zhangyu.springboot.multidatasource.config; import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionFactoryBean;
import org.mybatis.spring.SqlSessionTemplate;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.boot.autoconfigure.jdbc.DataSourceProperties;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary;
import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
import tk.mybatis.spring.annotation.MapperScan; import javax.sql.DataSource; // mysql数据源配置(主数据源)
@Configuration
@MapperScan(basePackages = "com.zhangyu.springboot.multidatasource.mapper.mysql", sqlSessionTemplateRef = "mysqlSqlSessionTemplate")
public class TestMysqlDataSourceConfig { // 注入数据源配置
@Primary
@Bean
@ConfigurationProperties(prefix = "spring.datasource.test-mysql")
public DataSourceProperties mysqlDataSourceProperties() {
return new DataSourceProperties();
} // 创建数据库连接
@Primary
@Bean
public DataSource mysqlDataSource() {
return mysqlDataSourceProperties().initializeDataSourceBuilder().build();
} // 创建session工厂
@Primary
@Bean
public SqlSessionFactory mysqlSessionFactory(@Qualifier("mysqlDataSource") DataSource dataSource) throws Exception {
SqlSessionFactoryBean sessionFactoryBean = new SqlSessionFactoryBean();
sessionFactoryBean.setDataSource(dataSource);
sessionFactoryBean.setMapperLocations(
new PathMatchingResourcePatternResolver().getResources("classpath*:mapper/*.xml"));
return sessionFactoryBean.getObject();
} // 创建事务管理(按需添加)
@Primary
@Bean
public DataSourceTransactionManager mysqlDataSourceTransactionManager() {
return new DataSourceTransactionManager(mysqlDataSource());
} // 会话管理
@Primary
@Bean
public SqlSessionTemplate mysqlSqlSessionTemplate(@Qualifier("mysqlSessionFactory") SqlSessionFactory sqlSessionFactory) {
return new SqlSessionTemplate(sqlSessionFactory);
}
}
次数据源(sqlserver)
package com.zhangyu.springboot.multidatasource.config; import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionFactoryBean;
import org.mybatis.spring.SqlSessionTemplate;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.boot.autoconfigure.jdbc.DataSourceProperties;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.boot.jdbc.DataSourceBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary;
import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
import tk.mybatis.spring.annotation.MapperScan; import javax.sql.DataSource; // sqlserver数据源配置
@Configuration
@MapperScan(basePackages = "com.zhangyu.springboot.multidatasource.mapper.sqlserver", sqlSessionTemplateRef = "sqlServerSqlSessionTemplate")
public class TestSqlServerDataSourceConfig { // 注入数据源配置
@Bean
@ConfigurationProperties(prefix = "spring.datasource.test-sqlserver")
public DataSourceProperties sqlServerDataSourceProperties() {
return new DataSourceProperties();
} // 创建数据库连接
@Bean
public DataSource sqlServerDataSource() {
return sqlServerDataSourceProperties().initializeDataSourceBuilder().build();
} // 创建session工厂
@Bean
public SqlSessionFactory sqlServerSessionFactory(@Qualifier("sqlServerDataSource") DataSource dataSource) throws Exception {
SqlSessionFactoryBean sessionFactoryBean = new SqlSessionFactoryBean();
sessionFactoryBean.setDataSource(dataSource);
sessionFactoryBean.setMapperLocations(
new PathMatchingResourcePatternResolver().getResources("classpath*:mapper/*.xml"));
return sessionFactoryBean.getObject();
} // 创建事务管理(按需添加)
@Bean
public DataSourceTransactionManager sqlServerDataSourceTransactionManager() {
return new DataSourceTransactionManager(sqlServerDataSource());
} // 会话管理
@Bean
public SqlSessionTemplate sqlServerSqlSessionTemplate(@Qualifier("sqlServerSessionFactory") SqlSessionFactory sqlSessionFactory) {
return new SqlSessionTemplate(sqlSessionFactory);
}
}
再啰嗦几句,mybatis是通过配置的扫描包和对应的sqlSessionTemplate来自动切换数据源,即通过在 @MapperScan 注解中配置 basePackages 和 sqlSessionTemplateRef。
四、尾声
启动项目,可以看到控制台打印如下信息:
INFO 12840 --- [)-26.12.195.117] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Starting...
INFO 12840 --- [)-26.12.195.117] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Start completed.
INFO 12840 --- [)-26.12.195.117] com.zaxxer.hikari.HikariDataSource : HikariPool-2 - Starting...
INFO 12840 --- [)-26.12.195.117] com.zaxxer.hikari.pool.PoolBase : HikariPool-2 - Driver does not support get/set network timeout for connections. (null)
INFO 12840 --- [)-26.12.195.117] com.zaxxer.hikari.HikariDataSource : HikariPool-2 - Start completed.
很明显实例化了两个 HikariPool ,实际使用又如何呢?
Usermapper连接的mysql数据库,TestMapper连接的sqlserver数据库:
//Service: public List<TbUser> getUserList() {
return userMapper.selectAll();
} public List<Test> getTestList() {
return testMapper.selectAll();
}
分别调用,能都正常获取数据。
至此,springboot双数据源配置完成,tk-mybatis也能正常使用。
********************************************************************************************************************************************************************
打完收工
********************************************************************************************************************************************************************
Springboot 多数据源配置,结合tk-mybatis的更多相关文章
- 基于注解实现SpringBoot多数据源配置
1.功能介绍 在实际的开发中,同一个项目中使用多个数据源是很常见的场景.最近在学习的过程中使用注解的方式实现了一个Springboot项目多数据源的功能.具体实现方式如下. 2.在applicatio ...
- springboot+多数据源配置
作者:纯洁的微笑 出处:http://www.ityouknow.com/ 起多数据源,一般都来解决那些问题呢,主从模式或者业务比较复杂需要连接不同的分库来支持业务.我们项目是后者的模式,网上找了很多 ...
- Spring-Boot 多数据源配置+动态数据源切换+多数据源事物配置实现主从数据库存储分离
一.基础介绍 多数据源字面意思,比如说二个数据库,甚至不同类型的数据库.在用SpringBoot开发项目时,随着业务量的扩大,我们通常会进行数据库拆分或是引入其他数据库,从而我们需要配置多个数据源. ...
- Springboot多数据源配置--数据源动态切换
在上一篇我们介绍了多数据源,但是我们会发现在实际中我们很少直接获取数据源对象进行操作,我们常用的是jdbcTemplate或者是jpa进行操作数据库.那么这一节我们将要介绍怎么进行多数据源动态切换.添 ...
- SpringBoot多数据源配置
准备环境: jdk1.8 eclipse tomcat8.0 第一步:在配置文件添加如下信息: spring.datasource.primary.url=jdbc:mysql://localhost ...
- SpringBoot多数据源配置事务
除了消费降级,这将会是娱乐继续下沉的一年. 36氪从多个信源处获悉,资讯阅读应用趣头条已经完成了腾讯领投的Pre-IPO轮融资,交易金额预计达上亿美元,本轮融资估值在13-15亿美金之间:完成此轮融资 ...
- SpringBoot常用数据源配置
#mysql8.X url: jdbc:mysql://localhost:3306/yourdbname?serverTimezone=UTC&useSSL=false&allowP ...
- springboot 不同类型多数据源配置及使用
springboot多数据源配置: datasource.master.jdbc=jdbc:mysql://localhost:3306/test?useUnicode=true&charac ...
- springboot v2.0.3版本多数据源配置
本篇分享的是springboot多数据源配置,在从springboot v1.5版本升级到v2.0.3时,发现之前写的多数据源的方式不可用了,捕获错误信息如: 异常:jdbcUrl is requir ...
随机推荐
- python中的守护线程
什么是守护线程:在后台运行,为其他线程提供服务的线程成为守护线程. 为什么要引入守护线程: thread模块不支持守护线程的概念,当主线程退出时,所有的子线程都将终止,不管它们是否仍在工作, 如果你不 ...
- 树的深度———树形DP
题目描述 输入 输出 样例 样例输入 样例输出 7 分析 这道题数据有1000000,把每一个顶点都枚举一次显然不现实,肯定会T掉 所以,我们还是从图中找规律 按照习惯,我们先把1号节点作为根节点模拟 ...
- SpringBoot + Vue + ElementUI 实现后台管理系统模板 -- 后端篇(一): 搭建基本环境、整合 Swagger、MyBatisPlus、JSR303 以及国际化操作
相关 (1) 相关博文地址: SpringBoot + Vue + ElementUI 实现后台管理系统模板 -- 前端篇(一):搭建基本环境:https://www.cnblogs.com/l-y- ...
- postman-7-前置请求脚本
前面讲了,tests初如何校验请求之后返回值是否正确 那前置脚本,就是处理,请求之前接口该如何处理,什么时候会用到呢? 比如:接口字段time,需要填入时间,而且这个是需要当前时间的,: 需要达到自动 ...
- [设计模式]工厂方法模式(Factory Method)
模式目的 定义一个用于创建对象的接口,让其子类来决定实例化哪个类. 工厂方法模式将类的实例化延迟到了子类中进行. 模式结构 组成部分 产品(Product) - 定义了产品功能的接口 具体产品(Con ...
- day05 程序与用户交互和基本运算符
程序与用户交互和基本运算符 目录 程序与用户交互和基本运算符 1.程序与用户交互 1.1什么是与用户交互 1.2为什么要与用户交互 1.3如何与用户交互 1.3.1格式化输出 2基本运算符 2.1算数 ...
- windows dos 批量重命名文件
描述 在工作中经常出现 在同一目录下有一些 很多相同扩展名的文件但是名字看起来很乱各不同,我们想将它们统一重命名一下统一的格式,如果一个个去改名字太麻烦了. 这里我门就可以使用windows下 dos ...
- CTFHub_技能树_SQL注入Ⅱ
SQL注入 MySQL结构 进行尝试: 尝试查看表名: 尝试查看列名: 发现无法直接输出: 使用时间注入脚本跑出结果: import requests import time session = re ...
- redis(十七):Redis 安装,部署(WINDOWS环境下)
1.下载Redis安装文件, 我选择的是 3.0.504 版本,有zip或msi可供下载. 2.解压缩后,打开安装目录 双击redis-server.exe启动redis服务器,双击redis-c ...
- 关于Excel去空格问题
做开发,导入导出是一项基本功能,基本每个系统都有. 导入日期字段难免碰到因为空格问题引起的日期格式化Bug 下面分享一项Excel识别空格以及去空格的方法. 一:识别空格技巧(不要相信你的眼睛,有些空 ...