这两天一直在配置双数据源,找了网上很多资料,有的资料写的太乱而且注释不清楚,类不全.像我这样的刚开始配置的新手很难看明白,今天终于配置成功了,我把我总结的整理一下,做个日志以防以后遇到问题
一.创建一个springboot项目其中需要的pom文件:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web-services</artifactId>
</dependency>
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>2.1.0</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<scope>runtime</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<scope>runtime</scope>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid</artifactId>
<version>1.0.28</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.16.10</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
二.下面开始配置我们的配置文件application.properties 我的事properties文件 如果是yml文件也是一样的就是写法不同而已
spring.datasource.first.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.first.url=jdbc:mysql://192.168.100.205:3306/storage_data?serverTimezone=UTC&useUnicode=true&characterEncoding=UTF-8&useSSL=false
spring.datasource.first.username=root
spring.datasource.first.password=root
spring.datasource.first.type=com.alibaba.druid.pool.DruidDataSource
spring.datasource.second.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.second.url=jdbc:mysql://192.168.100.205:3306/lltsj?serverTimezone=UTC&useUnicode=true&characterEncoding=UTF-8&useSSL=false
spring.datasource.second.username=root
spring.datasource.second.password=root
spring.datasource.second.type=com.alibaba.druid.pool.DruidDataSource
其中first和second自己随便写,只要将两个数据源区分开就可以
三.接下来就创建文件封装类(有几个数据源就创建几个,)
1.first数据源
package com.data.config;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;
/**
* Created by admin on 2019/11/7.
*/
@Data
@Component
@ConfigurationProperties(prefix = "spring.datasource.first")
public class FirstDataProperties {
String driverClassName;
String url;
String username;
String password;
}
2.second数据源
package com.data.config;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;
/**
* Created by admin on 2019/11/7.
*/
@Data
@Component
@ConfigurationProperties(prefix = "spring.datasource.second")
public class SecondDataProperties {
String driverClassName;
String url;
String username;
String password;
}
其中@ConfigurationProperties(prefix = “spring.datasource.second”)中prefix要和配置文件中配置数据源的名字一样
四.开始创建工厂,这里的代码是最重要的
@MapperScan(basePackages = “com.data.mapper.first”,sqlSessionTemplateRef = “firstSqlSessionTemplate”)此注解basePackages地址是自己对应数据源mapper地址,sqlSessionTemplateRef是我们创建工厂的名字,是自己起的,在代码最下面,如果没有特殊需要和我一样就可以
1.first数据源工厂
package com.data.config;
import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionFactoryBean;
import org.mybatis.spring.SqlSessionTemplate;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
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.jdbc.datasource.DataSourceTransactionManager;
import javax.sql.DataSource;
/**
* Created by admin on 2019/11/7.
*/
@Configuration
@MapperScan(basePackages = "com.data.mapper.first",sqlSessionTemplateRef = "firstSqlSessionTemplate")
public class FirstDataSourceConfig {
@Autowired
private FirstDataProperties firstprop;
//配置mybatis位置
static final String MAPPER_LOCATION = "classpath:mapping/*Mapper.xml";
//创建数据源
@Bean(name="firstDataSource")
@ConfigurationProperties(prefix = "spring.datasource.first")
public DataSource getFirstDataSource(){
DataSource build = DataSourceBuilder.create()
.driverClassName(firstprop.driverClassName)
.url(firstprop.url)
.username(firstprop.username)
.password(firstprop.password).build();
return build;
}
//创建SqlSessionFactory
@Bean(name = "firstSqlSessionFactory")
public SqlSessionFactory firstSqlSessionFactory(@Qualifier("firstDataSource") DataSource dataSource) throws Exception{
SqlSessionFactoryBean bean=new SqlSessionFactoryBean();
bean.setDataSource(dataSource);
//配置mybatis的位置工厂
bean.setMapperLocations(new PathMatchingResourcePatternResolver()
.getResources(FirstDataSourceConfig.MAPPER_LOCATION));
return bean.getObject();
}
//创建事务管理器
@Bean(name = "firstTransactionManager")
public DataSourceTransactionManager firstTransactionManager(@Qualifier("firstDataSource") DataSource dataSource){
return new DataSourceTransactionManager(dataSource);
}
//创建SqlSessionTemplate
@Bean(name = "firstSqlSessionTemplate")
public SqlSessionTemplate firstSqlSessionTemplate(@Qualifier("firstSqlSessionFactory") SqlSessionFactory sqlSessionFactory) throws Exception{
return new SqlSessionTemplate(sqlSessionFactory);
}
private Class getType(String type){
try {
return Class.forName(type);
}catch (ClassNotFoundException e){
e.printStackTrace();
}
return null;
}
}
2.second数据源
package com.data.config;
import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionFactoryBean;
import org.mybatis.spring.SqlSessionTemplate;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
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.jdbc.datasource.DataSourceTransactionManager;
import javax.sql.DataSource;
/**
* Created by admin on 2019/11/7.
*/
@Configuration
@MapperScan(basePackages = "com.data.mapper.second",sqlSessionTemplateRef = "secondSqlSessionTemplate")
public class SecondDataSourceConfig {
@Autowired
private SecondDataProperties secondprop;
//创建数据源
@Bean(name="secondDataSource")
@ConfigurationProperties(prefix = "spring.datasource.second")
@Primary
public DataSource getSecondDataSource(){
DataSource build = DataSourceBuilder.create()
.driverClassName(secondprop.driverClassName)
.url(secondprop.url)
.username(secondprop.username)
.password(secondprop.password).build();
return build;
}
//创建SqlSessionFactory
@Bean(name = "secondSqlSessionFactory")
@Primary
public SqlSessionFactory secondSqlSessionFactory(@Qualifier("secondDataSource") DataSource dataSource) throws Exception{
SqlSessionFactoryBean bean=new SqlSessionFactoryBean();
bean.setDataSource(dataSource);
return bean.getObject();
}
//创建事务管理器
@Bean(name = "secondTransactionManager")
@Primary
public DataSourceTransactionManager secondTransactionManager(@Qualifier("secondDataSource") DataSource dataSource){
return new DataSourceTransactionManager(dataSource);
}
//创建SqlSessionTemplate
@Bean(name = "secondSqlSessionTemplate")
@Primary
public SqlSessionTemplate secondSqlSessionTemplate(@Qualifier("secondSqlSessionFactory") SqlSessionFactory sqlSessionFactory) throws Exception{
return new SqlSessionTemplate(sqlSessionFactory);
}
private Class getType(String type){
try {
return Class.forName(type);
}catch (ClassNotFoundException e){
e.printStackTrace();
}
return null;
}
}
这样已经能用了,剩下的用法和我们用单数据源是一样的,就是分清哪个mapper是哪个数据源的,不要搞混就OK了
import com.data.mapper.second.SecondDataMapper;
import com.data.service.DataService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
/**
* Created by admin on 2019/8/19.
*/
@Service
public class DataServiceImpl implements DataService {
@Autowired
private FirstDataMapper firstDataMapper;
@Autowired
private SecondDataMapper secondDataMapper;
@Override
public String firstData() {
String a = firstDataMapper.firstData();
String b = secondDataMapper.firstData();
return a+b;
}
}
还有就是在启动类中加上
package com.data;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
@SpringBootApplication(exclude = {DataSourceAutoConfiguration.class})
public class IndataApplication {
public static void main(String[] args) {
SpringApplication.run(IndataApplication.class, args);
}
}
这是我项目的结构
这样就可以启动了