SpringBoot中动态数据源配置与使用详解

 更新时间:2024年10月21日 11:40:19   作者:码农阿豪  
在现代应用中,处理多数据源是常见的需求,在 Spring Boot 中,这样的需求可以通过动态数据源来轻松实现,本篇博客将详细介绍如何在 Spring Boot 中配置和使用动态数据源,并演示如何切换到指定的数据源,需要的朋友可以参考下

在现代应用中,处理多数据源是常见的需求。可能由于业务需要,或者为了实现读写分离,我们往往需要在同一个应用中配置多个数据源,并根据具体的操作选择不同的数据源。在 Spring Boot 中,这样的需求可以通过动态数据源来轻松实现。本篇博客将详细介绍如何在 Spring Boot 中配置和使用动态数据源,并演示如何切换到指定的数据源。

一、为什么要使用动态数据源?

  1. 业务隔离:在一些复杂的业务场景中,不同的模块可能需要连接不同的数据库。通过动态数据源配置,可以在同一个应用中隔离这些不同的数据库访问。

  2. 读写分离:为了提升系统的性能,通常会将读写操作分离到不同的数据库上。比如,将写操作放在主数据库,而读操作放在从数据库上。

  3. 数据库迁移:在系统迁移期间,可能需要在两个数据库之间切换,从而确保迁移的平稳进行。

二、Spring Boot 中的多数据源配置

我们将通过一个示例来介绍如何在 Spring Boot 中配置和使用动态数据源。假设我们有两个数据源,一个是 master,另一个是 adcontrol。master 数据源主要用于主业务数据库,而 adcontrol 数据源用于广告控制的相关数据存储。

1. 数据源配置

首先,我们需要在 application.yml 文件中配置两个数据源。

datasource:
  dynamic:
    primary: master # 默认使用master库
    strict: false   # 不使用严格模式
    datasource:
      master:
        url: jdbc:mysql://127.0.0.1:3306/test?serverTimezone=Asia/Shanghai&characterEncoding=utf8&useSSL=false
        username: root
        password: 123456
        driver-class-name: com.mysql.cj.jdbc.Driver
        hikari:
          connection-timeout: 30000
          max-lifetime: 1800000
          max-pool-size: 15
          min-idle: 5
          connection-test-query: select 1
          pool-name: YsxHikariCP
      adcontrol:
        url: jdbc:mysql://ip:3306/test2?serverTimezone=Asia/Shanghai&characterEncoding=utf8&useSSL=false
        username: test
        password: test
        driver-class-name: com.mysql.cj.jdbc.Driver

上述配置中,master 数据源是默认使用的数据源,而 adcontrol 数据源是备用的广告控制数据源。

2. 引入动态数据源依赖

为了让 Spring Boot 能够识别和使用这些动态数据源,我们需要引入动态数据源的依赖库。这里我们使用 dynamic-datasource-spring-boot-starter 这个开源库。

在 pom.xml 中添加如下依赖:

<dependency>
    <groupId>com.github.dynamic-datasource</groupId>
    <artifactId>dynamic-datasource-spring-boot-starter</artifactId>
    <version>3.2.1</version> <!-- 确保使用合适的版本 -->
</dependency>

3. 配置动态数据源

通过 DynamicDataSource,我们可以在应用中灵活切换数据源。下面是一个简单的 DynamicDataSource 配置示例:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import com.github.dynamic.datasource.DynamicRoutingDataSource;
import javax.sql.DataSource;
import org.springframework.boot.autoconfigure.jdbc.DataSourceBuilder;
import java.util.HashMap;
import java.util.Map;

@Configuration
public class DataSourceConfig {

    @Bean
    public DataSource dataSource() {
        DynamicRoutingDataSource dataSource = new DynamicRoutingDataSource();

        // 配置主数据源
        DataSource masterDataSource = DataSourceBuilder.create()
                .url("jdbc:mysql://127.0.0.1:3306/test1?serverTimezone=Asia/Shanghai&characterEncoding=utf8&useSSL=false")
                .username("root")
                .password("123456")
                .driverClassName("com.mysql.cj.jdbc.Driver")
                .build();

        // 配置广告控制数据源
        DataSource adcontrolDataSource = DataSourceBuilder.create()
                .url("jdbc:mysql://ip1:3306/test2?serverTimezone=Asia/Shanghai&characterEncoding=utf8&useSSL=false")
                .username("test")
                .password("test")
                .driverClassName("com.mysql.cj.jdbc.Driver")
                .build();

        // 将数据源放入Map
        Map<Object, Object> dataSourceMap = new HashMap<>();
        dataSourceMap.put("master", masterDataSource);
        dataSourceMap.put("adcontrol", adcontrolDataSource);

        dataSource.setDefaultTargetDataSource(masterDataSource);
        dataSource.setTargetDataSources(dataSourceMap);

        return dataSource;
    }
}

4. 使用 @DS 注解动态切换数据源

在服务层,我们可以通过 @DS 注解来指定当前方法应该使用哪个数据源。例如:

import com.github.dynamic.datasource.annotation.DS;
import org.springframework.stereotype.Service;

@Service
public class MyService {

    @DS("adcontrol")
    public void handleAdControlLogic() {
        // 使用adcontrol数据源执行操作
    }

    @DS("master")
    public void handleMasterLogic() {
        // 使用master数据源执行操作
    }
}

通过 @DS 注解,我们可以在方法层面灵活切换数据源,确保不同的业务逻辑使用正确的数据库连接。

三、异常处理与回滚

在使用多个数据源时,处理好事务和异常非常重要。如果在一个事务内执行了多个数据源的操作,那么事务的管理和异常处理就变得尤为关键。

Spring 提供了全局事务管理器的支持,可以配置为管理多个数据源的事务。但是在使用 dynamic-datasource 时,要特别注意确保在同一个事务中操作的多个数据源能够正确地提交或回滚。

例如:

import org.springframework.transaction.annotation.Transactional;

@Service
public class MyService {

    @Transactional
    @DS("master")
    public void processTransaction() {
        try {
            // 操作master数据库
            handleMasterLogic();

            // 切换到adcontrol数据源
            handleAdControlLogic();

        } catch (Exception e) {
            // 处理异常,可能需要回滚事务
            throw new RuntimeException("事务失败,进行回滚", e);
        }
    }

    @DS("adcontrol")
    public void handleAdControlLogic() {
        // 操作adcontrol数据库
    }

    @DS("master")
    public void handleMasterLogic() {
        // 操作master数据库
    }
}

在上面的代码中,如果 handleAdControlLogic 方法抛出了异常,那么整个事务将被回滚。

四、常见问题与解决方案

  1. 数据源切换失败

    • 确保 @DS 注解指向的名称与配置中的数据源名称完全一致。
    • 检查 DynamicDataSource 是否正确配置。
  2. 事务回滚失败

    • 确保在同一个事务中使用的所有数据源都支持事务管理。
    • 使用 @Transactional 注解来管理事务。
  3. 性能问题

    • 动态数据源切换可能会带来额外的性能开销。可以考虑使用连接池优化数据库连接管理。
  4. 无法连接数据库

    • 检查数据库连接配置,确保 urlusername 和 password 等参数正确。
    • 检查数据库服务器是否可达。

五、总结

通过动态数据源配置,Spring Boot 应用可以轻松应对多数据源的复杂需求。无论是业务隔离、读写分离,还是数据库迁移,动态数据源都能够提供灵活且高效的解决方案。

在实际应用中,合理规划和使用多数据源,可以显著提升系统的可扩展性和可靠性。在实现过程中,需要特别注意事务管理和异常处理,以确保数据的一致性和完整性。

通过本文的介绍,相信你已经掌握了在 Spring Boot 中配置和使用动态数据源的基本方法。在实际项目中,可以根据业务需求,进一步优化和扩展动态数据源的使用。希望本文能对你有所帮助。

以上就是SpringBoot中动态数据源配置与使用详解的详细内容,更多关于SpringBoot动态数据源的资料请关注脚本之家其它相关文章!

相关文章

  • 使用Spring框架实现用户登录

    使用Spring框架实现用户登录

    这篇文章主要为大家详细介绍了使用Spring框架实现用户登录,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2022-09-09
  • 教你使用springboot配置多数据源

    教你使用springboot配置多数据源

    发现有很多小伙伴还不会用springboot配置多数据源,今天特地给大家整理了本篇文章,文中有非常详细的图文介绍及代码示例,对正在学习java的小伙伴很有帮助,需要的朋友可以参考下
    2021-05-05
  • Java基于SpringBoot和tk.mybatis实现事务读写分离代码实例

    Java基于SpringBoot和tk.mybatis实现事务读写分离代码实例

    这篇文章主要介绍了Java基于SpringBoot和tk.mybatis实现事务读写分离代码实例,读写分离,基本的原理是让主数据库处理事务性增、改、删操作,而从数据库处理SELECT查询操作,数据库复制被用来把事务性操作导致的变更同步到集群中的从数据库,需要的朋友可以参考下
    2023-10-10
  • Spring Boot统一异常处理最佳实践(拓展篇)

    Spring Boot统一异常处理最佳实践(拓展篇)

    这篇文章主要给大家介绍了关于Spring Boot统一异常处理最佳实践(拓展篇)的相关资料,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2019-02-02
  • Java对象在JVM中的生命周期详解

    Java对象在JVM中的生命周期详解

    这篇文章主要介绍了Java对象在JVM中的生命周期详解,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
    2019-05-05
  • java连连看游戏菜单设计

    java连连看游戏菜单设计

    这篇文章主要为大家详细介绍了java连连看游戏菜单部分的设计代码,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2018-12-12
  • 教你轻松制作java视频播放器

    教你轻松制作java视频播放器

    这篇文章主要为大家详细介绍了如何编写属于自己的java视频播放器,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2017-06-06
  • Google Kaptcha验证码生成的使用实例说明

    Google Kaptcha验证码生成的使用实例说明

    这篇文章主要为大家介绍了Google Kaptcha验证码的使用实例说明,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2022-03-03
  • java基于Des对称加密算法实现的加密与解密功能详解

    java基于Des对称加密算法实现的加密与解密功能详解

    这篇文章主要介绍了java基于Des对称加密算法实现的加密与解密功能,结合实例形式详细分析了Des加密算法的功能、原理、使用方法与相关注意事项,需要的朋友可以参考下
    2017-01-01
  • intelliJ IDEA 多行选中相同内容的快捷键分享

    intelliJ IDEA 多行选中相同内容的快捷键分享

    这篇文章主要介绍了intelliJ IDEA 多行选中相同内容的快捷键分享,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2021-02-02

最新评论