果你在使用Druid连接池,确保DruidDataSource被配置为Spring的bean,并且Spring的事务管理器配置了正确的数据源。通过这些步骤,你应该能够
时间: 2025-04-07 14:06:12 浏览: 41
### DruidDataSource Spring 配置事务管理器 数据源集成
#### 多数据源配置概述
为了实现多数据源支持以及每个数据源拥有独立的事务管理功能,在 Spring Boot 中可以借助 Druid 连接池完成这一目标。以下是具体的配置步骤和代码示例。
---
#### YML 文件中的 Druid 连接池配置
在 `application.yml` 或 `application.properties` 文件中,需分别定义多个数据源的相关属性:
```yaml
spring:
datasource:
ds1:
url: jdbc:mysql://localhost:3306/db1?useUnicode=true&characterEncoding=utf8&serverTimezone=UTC
username: root
password: root
driver-class-name: com.mysql.cj.jdbc.Driver
type: com.alibaba.druid.pool.DruidDataSource
druid:
initial-size: 5
max-active: 20
min-idle: 5
max-wait: 60000
ds2:
url: jdbc:mysql://localhost:3306/db2?useUnicode=true&characterEncoding=utf8&serverTimezone=UTC
username: root
password: root
driver-class-name: com.mysql.cj.jdbc.Driver
type: com.alibaba.druid.pool.DruidDataSource
druid:
initial-size: 5
max-active: 20
min-idle: 5
max-wait: 60000
```
上述配置为两个不同的数据库实例设置了连接参数[^1]。
---
#### 定义数据源 Bean 和事务管理器
##### 第一步:创建通用方法类
用于简化重复性的 Bean 创建逻辑:
```java
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Bean;
import javax.sql.DataSource;
@Configuration
public class DataSourceConfig {
@Bean(name = "ds1")
@ConfigurationProperties(prefix = "spring.datasource.ds1")
public DataSource primaryDataSource() {
return new DruidDataSource();
}
@Bean(name = "ds2")
@ConfigurationProperties(prefix = "spring.datasource.ds2")
public DataSource secondaryDataSource() {
return new DruidDataSource();
}
}
```
此部分实现了基于前缀加载不同数据源的配置信息,并返回对应的 `DruidDataSource` 实例[^3]。
---
##### 第二步:为每个数据源创建独立的事务管理器
通过 `PlatformTransactionManager` 接口来定义事务管理器:
```java
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.annotation.Bean;
import org.springframework.jdbc.datasource.DataSourceTransactionManager;
@Bean(name = "transactionManagerDs1")
public DataSourceTransactionManager transactionManagerDs1(
@Qualifier("ds1") DataSource dataSource) {
return new DataSourceTransactionManager(dataSource);
}
@Bean(name = "transactionManagerDs2")
public DataSourceTransactionManager transactionManagerDs2(
@Qualifier("ds2") DataSource dataSource) {
return new DataSourceTransactionManager(dataSource);
}
```
这里分别为 `ds1` 和 `ds2` 提供了专属的事务管理器。
---
#### 使用自定义注解切换数据源
可以通过自定义注解动态切换当前线程使用的数据源:
```java
@Target({ElementType.METHOD, ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface DS {
String value(); // 数据源名称
}
```
接着编写拦截器以解析该注解并设置上下文中对应的数据源:
```java
@Component
public class DynamicDataSourceInterceptor implements MethodInterceptor {
@Override
public Object invoke(MethodInvocation invocation) throws Throwable {
DS currentDSAnnotation = AnnotationUtils.findAnnotation(invocation.getMethod(), DS.class);
if (currentDSAnnotation != null && StringUtils.hasText(currentDSAnnotation.value())) {
DynamicDataSourceContextHolder.setDataSourceKey(currentDSAnnotation.value());
}
try {
return invocation.proceed();
} finally {
DynamicDataSourceContextHolder.clearDataSourceKey();
}
}
}
```
最后注册 AOP 切面规则以便生效[^4]。
---
#### 动态数据源持有者工具类
提供一种机制存储当前请求所关联的具体数据源键名:
```java
public class DynamicDataSourceContextHolder {
private static final ThreadLocal<String> CONTEXT_HOLDER = new ThreadLocal<>();
public static void setDataSourceKey(String key) {
CONTEXT_HOLDER.set(key);
}
public static String getDataSourceKey() {
return CONTEXT_HOLDER.get();
}
public static void clearDataSourceKey() {
CONTEXT_HOLDER.remove();
}
}
```
以上组件共同协作完成了运行期灵活切换的功能需求[^2]。
---
#### 总结
综上所述,利用 Druid 的高性能特性配合 Spring Framework 提供的强大扩展能力,能够轻松达成复杂场景下的业务诉求——即多套异构关系型数据库间无缝交互的同时保障各自操作的一致性和隔离度。
阅读全文
相关推荐













