带你看懂RuoYi动态数据源切换

news2025/2/25 6:25:06

文章目录

  • 数据源是什么
  • 一、spring中是如何处理各种数据源的?
    • 1.开搞springboot
    • 2.创建一个测试类
  • 二、有了如上的理论,那么想想动态切换数据源吧
    • 参考若依的动态数据源配置
  • 总结


数据源是什么

数据源,对于java来说,就是可用的数据库,那么我平时开发的springboot springcloud项目,那么也就是yml或者properties中的链接信息, 例如 mysql redis influx mongodb sqlserver clickhouse nebula-graph …
一般在spring中,都已经对其做好了封装


一、spring中是如何处理各种数据源的?

那就不得不说下JdbcTemplate 了,只要是各种遵循了jdbc标准的数据源,也就是大部分的关系型数据库,都是可以通过它来操作的;简直就是神奇~~ 怎么使用呢?

1.开搞springboot

搞一个springboot项目 由于我使用了mysql,所以还引入了mysql驱动包

	  <dependency>
          <groupId>org.springframework.boot</groupId>
          <artifactId>spring-boot-starter-jdbc</artifactId>
      </dependency>
      <dependency>
          <groupId>mysql</groupId>
          <artifactId>mysql-connector-java</artifactId>
         <scope>runtime</scope>
      </dependency>

然后在yml加入相应配置

spring:
  datasource:
    driver-class-name: com.mysql.jdbc.Driver
    url: jdbc:mysql://xxxxx:3307/yuque
    username: root
    password: 123456

2.创建一个测试类

@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.DEFINED_PORT)
class WordApplicationTests1 {

    @Test
    void contextLoads() {
    }

    @Autowired
    JdbcTemplate jdbcTemplate;

    @SneakyThrows
    @Test
    public void query() {
        List<Bom> bomList = jdbcTemplate.query("select DISTINCT * from bom", new BeanPropertyRowMapper<>(Bom.class));

        System.out.println(JSONUtil.toJsonStr(bomList));
    }
}

相当于可以了,用的就是yml中的配置查询的数据库
在这里插入图片描述

  • 我有一个想法,我想查询一个其他的库的数据,但是之前的yml中的我还想用

改造后,变成了

@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.DEFINED_PORT)
class WordApplicationTests1 {

    @Test
    void contextLoads() {
    }

    @Autowired
    JdbcTemplate jdbcTemplate;

    @SneakyThrows
    @Test
    public void query() {
        List<Bom> bomList = jdbcTemplate.query("select DISTINCT * from bom", new BeanPropertyRowMapper<>(Bom.class));

        System.out.println(JSONUtil.toJsonStr(bomList));

        Properties properties = new Properties();
        properties.put("url", "jdbc:mysql://localhost:3306/test?useSSL=false&useUnicode=true&characterEncoding=utf-8&zeroDateTimeBehavior=convertToNull&transformedBitIsBoolean=true&tinyInt1isBit=false&allowMultiQueries=true&serverTimezone=GMT%2B8&allowPublicKeyRetrieval=true");
        properties.put("username", "root");
        properties.put("driverClassName", "com.mysql.jdbc.Driver");
        properties.put("password", "root");

        DataSource dataSource = DruidDataSourceFactory.createDataSource(properties);
        JdbcTemplate template = new JdbcTemplate(dataSource);

        List<Bom> list = template.query("select * from bom", new BeanPropertyRowMapper<>(Bom.class));
        System.out.println(JSONUtil.toJsonStr(list));
    }
}

还是能用的,两个都能查询出数据
在这里插入图片描述
那…请小伙伴思考下,如果是用jdbc弄一个动态数据源,是不是也不是很难,我需要用哪个库的信息,就让他加载哪个库的配置信息就ok了呀.对吧?
甚至,我可以将配置信息放入数据库中,启动后,一次性加载到内存,并实例化相应的datasource 实例,然后在实例化相应的jdbctemplete,放入到的全局中,那么我就可以自如切换了!!!

二、有了如上的理论,那么想想动态切换数据源吧

参考若依的动态数据源配置

若依
大体思路如下:

  • 首先利用本地线程搞一个缓存,目的是为了存放当前可用的数据源,这样就可以设置/移除 某个数据源了;
DynamicDataSourceContextHolder 仅仅是个缓存
  • 由于为了使用方便,所以他自定义了注解,用来切换数据源,也就是更改上面的当前线程缓存,那么自定义之后,就需要通过切面去实现这个自定义的注解,里面的中心思想就是获取传入的可用数据源(可能有多个),替换之为当前数据源(只能有一个);
DataSourceAspect 切面实现切换
  • 那么多个数据源是从哪里来的呢,是在项目启动的时候,他就已经把可用数据源都实例化好了,然后存放起来了,就像我之前分析的那样,关键点就是 实现这个方法 AbstractRoutingDataSource 其中 放入一个map 就是数据源本尊了
DruidConfig 把所有数据源都加载进去了
  • 之后就可以通过map.getkey 那样,获取到自己想要的数据源了;然后更改本地线程的数据源
  • 切换之后,查询的时候,就会重新查询到当前设置后的数据源,然后再去查询

重点中的重点

DynamicDataSource extends AbstractRoutingDataSource

@Override
   protected Object determineCurrentLookupKey(){
       return DynamicDataSourceContextHolder.getDataSourceType();// 每次执行都会重新获取新值
   }

在这里插入图片描述


总结

通过此次JdbcTemplate 的数据源切换,想到了之前看过的若依项目中的多数据源切换问题,这次带着我自己的想法去看,果然再次阅读,收获颇丰;算是彻底看懂了吧;
希望我的理解能为你带来启发

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/387318.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

算机网络安全基础知识5:sql注入漏洞攻击,DVWA演示sql注入漏洞,如何利用sql注入查看数据库信息,sqlmap,sql注入漏洞的防御

算机网络安全基础知识5:sql注入漏洞攻击&#xff0c;DVWA演示sql注入漏洞&#xff0c;如何利用sql注入查看数据库信息&#xff0c;sqlmap&#xff0c;sql注入漏洞的防御 2022找工作是学历、能力和运气的超强结合体&#xff0c;遇到寒冬&#xff0c;大厂不招人&#xff0c;可能…

Unity/C#------委托与事件(一篇文章彻底搞懂...)

一&#xff1a;委托 所有的代码语言创造者母语都是英语&#xff0c;我们从英语翻译到中文的过程中难免会存在一些不太能还原本意的词&#xff0c;比如我之前一直不理解构造函数和析构函数&#xff0c;只知道这俩货作用相反&#xff0c;直到我看到了它的英文意思&#xff0c;Con…

spring重点整理篇--springMVC(嘿嘿,开心哟)

Spring MVC是的基于JavaWeb的MVC框架&#xff0c;是Spring框架中的一个组成部分(WEB模块) MVC设计模式&#xff1a; Controller&#xff08;控制器&#xff09; Model&#xff08;模型&#xff09; View&#xff08;视图&#xff09; 重点来了&#x1f604; SpringMVC的工作机制…

Nginx+Tomcat实现负载均衡、动静分离(脚本方法)

一、Nginx 负载均衡实现原理1、Nginx 实现负载均衡是通过反向代理实现反向代理&#xff08;Reverse Proxy&#xff09; 是指以 代理服务器&#xff08;例&#xff1a;Nginx&#xff09; 来接受 internet 上的连接请求&#xff0c;然后将请求转发给内部网络上的服务器&#xff0…

【PGMAN:无监督的生成式多对抗网络】

PGMAN: An Unsupervised Generative Multiadversarial Network for Pansharpening &#xff08;PGMAN&#xff1a;一种无监督的生成式多对抗网络&#xff09; 全色锐化的目的是融合低分辨率多光谱&#xff08;MS&#xff09;图像和由卫星获取的高分辨率全色&#xff08;PAN&a…

OnlyOffice验证(三)OnlyOffice编译结果自制Docker镜像

OnlyOffice验证&#xff08;三&#xff09;OnlyOffice编译结果自制Docker镜像 之前验证了OnlyOffice验证&#xff08;二&#xff09;在Centos7上部署OnlyOffice编译结果&#xff0c;由于现在普遍都是容器化部署&#xff0c;所以还是验证下Doker镜像打包是否可行&#xff0c;因为…

渗透five86-2

kali的ip为192.168.56.104&#xff0c;利用nmap或arp-scan -l查看发现了靶机ip192.168.56.120这里存在20、21、80端口&#xff0c;这边需要将靶机ip进行域名绑定&#xff0c;对/etc/hosts改写&#xff0c;将192.168.56.120 与five86-2绑定输入ip后&#xff0c;发现了有log in由…

Kubernetes的网络架构及其安全风险

本博客地址&#xff1a;https://security.blog.csdn.net/article/details/129137821 一、常见的Kubernetes网络架构 如图所示&#xff1a; 说明&#xff1a; 1、集群由多个节点组成。 2、每个节点上运行若干个Pod。 3、每个节点上会创建一个CNI网桥&#xff08;默认设备名称…

Qt——自定义界面之QStyle

1. Qt控件结构简介 首先我们要来讲讲GUI控件结构&#xff0c;这里以QComboBox为例&#xff1a; 一个完整的控件由一种或多种GUI元素构成&#xff1a; Complex Control Element。Primitive Element。Control Element。 1.1 Complex Control Element Complex control elements …

【C语言跬步】——指针数组和数组指针(指针进阶)

一.指针数组和数组指针的区别 1.指针数组是数组&#xff0c;是一种存放指针的数组&#xff1b; 例如&#xff1a; int* arr[10]; 2.数组指针是指针&#xff0c;是一种指向数组的指针&#xff0c;存放的是数组的地址&#xff1b; 例如&#xff1a; int arr[5]; int (p)[5]&a…

Redis学习(二):Redis安装测试

概述 Redis是什么 Redis, Remote Dictionary Server, 即远程字典服务。免费开源的数据库。 由C语言编写&#xff0c;支持网络&#xff0c;可基于内存亦可持久化的日志型、KV数据库&#xff0c;并提供所种语言的API。 Redis能干嘛 用于内存存储&#xff0c;持久化。rdb、ao…

[学习笔记]黑马程序员Spark全套视频教程,4天spark3.2快速入门到精通,基于Python语言的spark教程

文章目录视频资料&#xff1a;一、Spark基础入门&#xff08;环境搭建、入门概念&#xff09;第二章&#xff1a;Spark环境搭建-Local2.1 课程服务器环境2.2 Local模式基本原理2.3 安装包下载2.4 Spark Local模式部署第三章&#xff1a;Spark环境搭建-StandAlone3.1 StandAlone…

驾考笔记_2023

科目一1> 扣分制度1.1> 超速1.2> 超载1.3> 车牌1.4> 速记口诀2> 满分学习2.1> 消分学习2.2> 满分重考&#xff1b;3> 罚款制度3.1> 考证3.2> 审验教育3.3> 其他4> 车速规定4.1> 高速_最低限速4.2> 普路_最高限速5> 证件相关5.…

双指针法|位运算|离散化|区间合并

目录 双指针算法 位运算 离散化 序列合并 双指针算法 题目描述&#xff1a;1.输入n个单词&#xff0c;每个单词在输入的时候按空格隔开&#xff0c;之后打印出每个单词且换行 #include<iostream> #include <string>using namespace std; int main() {strin…

计算机网络中的原码、反码、补码

写在前面 原码、反码、补码是计算机组成原理中的概念&#xff0c;是计算机网络的基础知识之一。这些概念是为了处理二进制数的符号位而引入的&#xff0c;常用于计算机中的整数运算&#xff0c;也常用于数据存储和传输等领域。因此&#xff0c;了解和掌握这些概念对于理解计算机…

软测入门(五)接口测试Postman

Postman 一款Http接口收工测试工具。如果做自动化测试会使用jemter做。 安装 去官网下载即可。 https://www.postman.com/downloads/?utm_sourcepostman-home 功能介绍 页面上的单词基本上都能了解&#xff0c;不多介绍。 转代码&注释 可将接口的访问转为其他语言的…

一款小巧、开源免费、可观性强的流量监控软件——TrafficMonitor

名人说&#xff1a;君子生非异也&#xff0c;善假于物也。——荀子 Code_流苏(CSDN)&#xff08;一个喜欢古诗词和编程的Coder&#x1f60a;&#xff09; o(‐&#xff3e;▽&#xff3e;‐)o很高兴你打开了这篇博客&#xff0c;跟着步骤一步步尝试安装吧。✧ 目录背景缘由一、…

自动驾驶目标检测项目实战(一)—基于深度学习框架yolov的交通标志检测

自动驾驶目标检测项目实战——基于深度学习框架yolov的交通标志检测 目前目标检测算法有很多&#xff0c;流行的就有faster-rnn和yolov&#xff0c;本文使用了几年前的yolov3框架进行训练&#xff0c;效果还是很好&#xff0c;当然也可以使用更高版本的Yolov进行实战。本代码使…

分布式事务之TCC与SAGA

分布式事务之TCC与SAGA 在《关于分布式事务的理解》&#xff0c;介绍了可靠消息队列的实现原理&#xff0c;虽然它也能保证最终的结果是相对可靠的&#xff0c;过程也足够简单&#xff08;相对于 TCC 来说&#xff09;&#xff0c;但现在你已经知道&#xff0c;可靠消息队列的…

从零起步认识XAML

新建WPF项目 在Visual Studio 2022中&#xff0c;选择"创建新项目" 选择“WPF Application” 点击下一步 点击创建。 执行DebugStart Debugging菜单命令&#xff0c;或者快捷键为F5&#xff0c;或者工具栏上的图标。 在Solution Explorer窗口&#xff08;ViewSoluti…