iis服务器助手广告广告
返回顶部
首页 > 资讯 > 精选 >mybatis中怎么实现读写分离
  • 524
分享到

mybatis中怎么实现读写分离

2023-06-20 19:06:27 524人浏览 独家记忆
摘要

本篇文章为大家展示了mybatis中怎么实现读写分离,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。1、spring aop实现首先application-test.yml增加如下数据源的配置spri

本篇文章为大家展示了mybatis中怎么实现读写分离,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。

1、spring aop实现

首先application-test.yml增加如下数据源的配置

spring:  datasource:    master:      jdbc-url: jdbc:mysql://master域名:3306/test      username: root      passWord: 123456      driver-class-name: com.Mysql.jdbc.Driver    slave1:      jdbc-url: jdbc:mysql://slave域名:3306/test      username: root   # 只读账户      password: 123456      driver-class-name: com.mysql.jdbc.Driver    slave2:      jdbc-url: jdbc:mysql://slave域名:3306/test      username: root   # 只读账户      password: 123456      driver-class-name: com.mysql.jdbc.Driver
package com.cjs.example.enums;public enum DBTypeEnum {    MASTER, SLAVE1, SLAVE2;}

定义ThreadLocal上下文,将当前线程的数据源进行动态修改

public class DBContextHolder {    private static  volatile ThreadLocal<DBTypeEnum> contextHolder = new ThreadLocal<>();    public static synchronized void set(DBTypeEnum dbType) {        contextHolder.set(dbType);    }    public static synchronized DBTypeEnum get() {        return contextHolder.get();    }    public static void master() {        set(DBTypeEnum.MASTER);    }    public static void slave() {        set(DBTypeEnum.SLAVE1);    }    public static void slave2(){ set(DBTypeEnum.SLAVE2); }    // 清除数据源名    public static void clearDB() {        contextHolder.remove();    }}

重写mybatis数据源路由接口,在此修改数据源为我们上一块代码设置的上下文的数据源

public class MyRoutingDataSource extends AbstractRoutingDataSource {    @Nullable    @Override    protected Object determineCurrentLookupKey() {        DBTypeEnum dbTypeEnum=DBContextHolder.get();        return dbTypeEnum;    }}

将yml配置的多数据源手动指定注入

@Configurationpublic class DataSourceConfig {    @Bean    @ConfigurationProperties("spring.datasource.master")    public DataSource masterDataSource() {        return DataSourceBuilder.create().build();    }    @Bean    @ConfigurationProperties("spring.datasource.slave1")    public DataSource slave1DataSource() {        return DataSourceBuilder.create().build();    }    @Bean    public DataSource myRoutingDataSource(@Qualifier("masterDataSource") DataSource masterDataSource,                                          @Qualifier("slave1DataSource") DataSource slave1DataSource) {        Map<Object, Object> targetDataSources = new HashMap<>();        targetDataSources.put(DBTypeEnum.MASTER, masterDataSource);        targetDataSources.put(DBTypeEnum.SLAVE1, slave1DataSource);        MyRoutingDataSource myRoutingDataSource = new MyRoutingDataSource();        myRoutingDataSource.setDefaultTargetDataSource(masterDataSource);        myRoutingDataSource.setTargetDataSources(targetDataSources);        return myRoutingDataSource;    }}

sqlsession注入以上我们配置的datasource路由

@EnableTransactionManagement@Configuration@Import({TableSegInterceptor.class})public class MyBatisConfig {    @Resource(name = "myRoutingDataSource")    private DataSource myRoutingDataSource;    @Autowired    private MybatisConfigProperty mybatisConfigProperty;    @Autowired    private TableSegInterceptor tableSegInterceptor;    @Bean    public SqlSessionFactory sqlSessionFactory() throws Exception {        SqlSessionFactoryBean sqlSessionFactoryBean = new SqlSessionFactoryBean();        sqlSessionFactoryBean.setDataSource(myRoutingDataSource);        // SpringBoot项目集成mybatis打包为jar运行时setTypeAliasesPackage无效解决        VFS.addImplClass(SpringBootVFS.class);        sqlSessionFactoryBean.setMapperLocations(                new PathMatchingResourcePatternResolver().getResources(mybatisConfigProperty.getMapperLocations()));        sqlSessionFactoryBean.setTypeAliasesPackage(mybatisConfigProperty.getTypeAliasesPackage());        sqlSessionFactoryBean.setConfigLocation(                new PathMatchingResourcePatternResolver().getResource(mybatisConfigProperty.getConfigLocation()));        sqlSessionFactoryBean.setPlugins(new Interceptor[]{tableSegInterceptor});        return sqlSessionFactoryBean.getObject();    }    @Bean    public PlatfORMTransactionManager platformTransactionManager() {        return new DataSourceTransactionManager(myRoutingDataSource);    }}

spring aop拦截指定前缀的service方法,并设置对应所属的上下文

@Aspect@Componentpublic class DataSourceAop {    @Pointcut("!@annotation(com.ask.student.interceptor.annotation.Master) " +            "&& (execution(* com.ask.student.service..*.select*(..)) " +            "|| execution(* com.ask.student.service..*.get*(..))" +            "|| execution(* com.ask.student.service..*.find*(..))" +            ")")    public void readPointcut() {    }    @Pointcut("@annotation(com.ask.student.interceptor.annotation.Master) " +            "|| execution(* com.ask.student.service..*.insert*(..)) " +            "|| execution(* com.ask.student.service..*.clean*(..)) " +            "|| execution(* com.ask.student.service..*.reset*(..)) " +            "|| execution(* com.ask.student.service..*.add*(..)) " +            "|| execution(* com.ask.student.service..*.update*(..)) " +            "|| execution(* com.ask.student.service..*.edit*(..)) " +            "|| execution(* com.ask.student.service..*.delete*(..)) " +            "|| execution(* com.ask.student.service..*.remove*(..))")    public void writePointcut() {    }    @Before("readPointcut()")    public void read() {        DBContextHolder.slave();    }    @Before("writePointcut()")    public void write() {        DBContextHolder.master();    }    @After("readPointcut()||writePointcut()")    public void afterSwitchDS(){        DBContextHolder.clearDB();    }}

以上最后一个方法的作用,在拦截器中获取后及时清除避免导致来回切换当前线程变量延迟问题导致某些操作的数据源错误

DBContextHolder.clearDB();

@After("readPointcut()||writePointcut()")

public void afterSwitchDS(){

DBContextHolder.clearDB();

}

2、mybatis-plus的实现方式

这个方式配置简单,代码少,很多事情mybatis-plus都已经做好了,推荐使用

yml配置如下

  datasource:    dynamic:      primary: master  #设置默认的数据源或者数据源组,默认值即为master      strict: false #设置严格模式,默认false不启动. 启动后在未匹配到指定数据源时候会抛出异常,不启动则使用默认数据源.      datasource:        master:          url: jdbc:mysql://xxx:3306/db0?useUnicode=true&characterEncoding=UTF-8&autoReconnect=true&useSSL=false&zeroDateTimeBehavior=convertToNull&serverTimezone=Asia/Shanghai          username: admin          password: 123456          driver-class-name: com.mysql.cj.jdbc.Driver          type: com.zaxxer.hikari.HikariDataSource          hikari:            minimum-idle: 5            maximum-pool-size: 15            auto-commit: true            idle-timeout: 30000            pool-name: springHikariCP            max-lifetime: 1800000            connection-timeout: 30000            connection-test-query: SELECT 1        slave1:          url: jdbc:mysql://xxx:3306/db2?useUnicode=true&characterEncoding=UTF-8&autoReconnect=true&useSSL=false&zeroDateTimeBehavior=convertToNull&serverTimezone=Asia/Shanghai          username: admin          password: 123456          driver-class-name: com.mysql.cj.jdbc.Driver          type: com.zaxxer.hikari.HikariDataSource          hikari:            minimum-idle: 5            maximum-pool-size: 15            auto-commit: true            idle-timeout: 30000            pool-name: springHikariCP            max-lifetime: 1800000            connection-timeout: 30000            connection-test-query: SELECT 1        slave2:          url: jdbc:mysql://xxx:3306/db3?useUnicode=true&characterEncoding=UTF-8&autoReconnect=true&useSSL=false&zeroDateTimeBehavior=convertToNull&serverTimezone=Asia/Shanghai          username: admin          password: 123456          driver-class-name: com.mysql.cj.jdbc.Driver          type: com.zaxxer.hikari.HikariDataSource          hikari:            minimum-idle: 5            maximum-pool-size: 15            auto-commit: true            idle-timeout: 30000            pool-name: springHikariCP            max-lifetime: 1800000            connection-timeout: 30000            connection-test-query: SELECT 1

使用起来非常简单,只需要加上这个master的注解即可

@Override    @DS("master")    public DestMedia getOneByCodeFromEpg(String code) {        QueryWrapper queryWrapper = new QueryWrapper();        queryWrapper.eq("code", code);        return super.getOne(queryWrapper);    }

上述内容就是mybatis中怎么实现读写分离,你们学到知识或技能了吗?如果还想学到更多技能或者丰富自己的知识储备,欢迎关注编程网精选频道。

--结束END--

本文标题: mybatis中怎么实现读写分离

本文链接: https://www.lsjlt.com/news/299637.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • mybatis中怎么实现读写分离
    本篇文章为大家展示了mybatis中怎么实现读写分离,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。1、spring aop实现首先application-test.yml增加如下数据源的配置spri...
    99+
    2023-06-20
  • MyCat中怎么实现读写分离
    这期内容当中小编将会给大家带来有关MyCat中怎么实现读写分离,文章内容丰富且以专业的角度为大家分析和叙述,阅读完这篇文章希望大家可以有所收获。1、mycat实现读写分离这里没有用到mysql03主机,读写...
    99+
    2024-04-02
  • SpringBoot怎么实现读写分离
    这篇文章主要讲解了“SpringBoot怎么实现读写分离”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“SpringBoot怎么实现读写分离”吧!前言根据公司业务需求,项目需要读写分离,所以记...
    99+
    2023-06-30
  • redis读写分离怎么实现
    Redis读写分离可以通过以下几种方式实现:1. 主从复制(Master-Slave):将一个Redis实例作为主节点(Master...
    99+
    2023-09-06
    redis
  • 怎么实现mysql读写分离
    这篇文章主要介绍“怎么实现mysql读写分离”,在日常操作中,相信很多人在怎么实现mysql读写分离问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”怎么实现mysql读写分离”...
    99+
    2024-04-02
  • 带你了解mybatis如何实现读写分离
    目录1、spring aop实现2、mybatis-plus的实现方式总结1、spring aop实现 首先application-test.yml增加如下数据源的配置 spri...
    99+
    2024-04-02
  • SpringBoot项目中怎么实现MySQL读写分离
    这篇文章主要介绍了SpringBoot项目中怎么实现MySQL读写分离的相关知识,内容详细易懂,操作简单快捷,具有一定借鉴价值,相信大家阅读完这篇SpringBoot项目中怎么实现MySQL读写分离文章都会有所收获,下面我们一起来看看吧。1...
    99+
    2023-07-02
  • SpringBoot+MyBatis+AOP实现读写分离的示例代码
    目录一、 MySQL 读写分离1.1、如何实现 MySQL 的读写分离? 1.2、MySQL 主从复制原理?1.3、MySQL 主从同步延时问题(精华)二、SpringBo...
    99+
    2024-04-02
  • SpringBoot中怎么利用MyCat实现读写分离
    SpringBoot中怎么利用MyCat实现读写分离,很多新手对此不是很清楚,为了帮助大家解决这个难题,下面小编将为大家详细讲解,有这方面需求的人可以来学习下,希望你能有所收获。MySQL配置主从关系说明 192.168.0.10...
    99+
    2023-06-16
  • php中怎么实现Mysql读写分离操作
    php中怎么实现Mysql读写分离操作,很多新手对此不是很清楚,为了帮助大家解决这个难题,下面小编将为大家详细讲解,有这方面需求的人可以来学习下,希望你能有所收获。连接案例:<php require...
    99+
    2024-04-02
  • MySQL中如何实现读写分离
    MySQL中如何实现读写分离,针对这个问题,这篇文章详细介绍了相对应的分析和解答,希望可以帮助更多想解决这个问题的小伙伴找到更简单易行的方法。一,创建Master数据库的配置文件vi master...
    99+
    2024-04-02
  • 怎么在java中利用spring实现读写分离
    怎么在java中利用spring实现读写分离?相信很多没有经验的人对此束手无策,为此本文总结了问题出现的原因和解决方法,通过这篇文章希望你能解决这个问题。1.  背景我们一般应用对数据库而言都是“读多写少”,也就说对数据库读取数据...
    99+
    2023-05-30
    spring java
  • 如何在Spring中使用MyBatis实现数据的读写分离
    如何在Spring中使用MyBatis实现数据的读写分离?很多新手对此不是很清楚,为了帮助大家解决这个难题,下面小编将为大家详细讲解,有这方面需求的人可以来学习下,希望你能有所收获。其实现原理如下:通过Spring AOP对dao层接口进行...
    99+
    2023-05-31
    spring mybatis 读写分离
  • SpringBoot中怎么实现一个读写分离组件
    这期内容当中小编将会给大家带来有关SpringBoot中怎么实现一个读写分离组件,文章内容丰富且以专业的角度为大家分析和叙述,阅读完这篇文章希望大家可以有所收获。1.pom.xml配置文件<depen...
    99+
    2024-04-02
  • 浅析php+mysql怎么实现读写分离
    MySQL作为目前最流行的数据库之一,在应用中大量被使用。在高并发和数据量较大的情况下,由于MySQL的读写并发性能不足,为了提高MySQL的并发性能,读写分离成为了必要的方案。读写分离的原理是将读操作和写操作分别放在不同的MySQL实例上...
    99+
    2023-05-14
    读写分离 php mysql
  • 使用Django怎么实现MySQL读写分离
    本篇文章为大家展示了使用Django怎么实现MySQL读写分离,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。主从同步介绍和优点在多台数据服务器中,分为主服务器和从服...
    99+
    2024-04-02
  • 使用Mycat怎么实现MySQL读写分离
    今天就跟大家聊聊有关使用Mycat怎么实现MySQL读写分离,可能很多人都不太了解,为了让大家更加了解,小编给大家总结了以下内容,希望大家根据这篇文章可以有所收获。搭建环境操作系统:CentOS-6.5-x...
    99+
    2024-04-02
  • Java基于JNDI怎么实现读写分离
    这篇文章主要介绍“Java基于JNDI怎么实现读写分离”,在日常操作中,相信很多人在Java基于JNDI怎么实现读写分离问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”Java基于JNDI怎么实现读写分离”的疑...
    99+
    2023-06-22
  • MySQL 中间件Atlas 实现读写分离
    〇 Atlas架构介绍 Atlas是Qihoo360开发的一个中间件,位于Client和MySQL Server中间层,可以作为读写分离,分库分表中间件。 对于MySQL Server而言,Atlas像是...
    99+
    2024-04-02
  • mysql中Oneproxy如何实现读写分离
    这篇文章将为大家详细讲解有关mysql中Oneproxy如何实现读写分离,小编觉得挺实用的,因此分享给大家做个参考,希望大家阅读完这篇文章后可以有所收获。基本架构: 写请求全部定向到主库,数据通过日志异步复...
    99+
    2024-04-02
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作