springboot 动态多数据源


springboot 动态多数据源

 

应用:同一个应用中使用多个数据库,根据需要切换数据库

 

 

*********************

相关类与接口

 

AbstractRoutingDataSource

public abstract class AbstractRoutingDataSource extends AbstractDataSource implements InitializingBean {


************
部分字段

    @Nullable
    private Map<Object, Object> targetDataSources;   //目标数据源

    @Nullable
    private Object defaultTargetDataSource;         //默认数据源


************
常用方法

    public void setTargetDataSources(Map<Object, Object> targetDataSources) {
        this.targetDataSources = targetDataSources;
    }                         //设置目标数据源

    public void setDefaultTargetDataSource(Object defaultTargetDataSource) {
        this.defaultTargetDataSource = defaultTargetDataSource;
    }                         //设置默认数据源

    @Nullable
    protected abstract Object determineCurrentLookupKey();
                              //抽象方法,设置数据源的key

 

 

*********************

示例:同一应用中向不同的数据库中插入数据

 

数据库h1:表user

数据库h2:表person

 

******************

config 层

 

DynamicDatasource:动态数据源切换

public class DynamicDataSource extends AbstractRoutingDataSource {

    private ThreadLocal<DataSource_Enum> threadLocal=new ThreadLocal<>();

    public void switchDataSource(DataSource_Enum dataSource_enum){
        threadLocal.set(dataSource_enum);
    }

    @Override
    protected Object determineCurrentLookupKey() {
        return threadLocal.get();
    }

 

DataConfig:配置数据源

@Configuration
@EnableAspectJAutoProxy
@MapperScan("com.example.demo.dao")
public class DataConfig {

    @Bean("one")
    @ConfigurationProperties("spring.datasource.druid.one")
    public DataSource initOneDataSource(){
        return DruidDataSourceBuilder.create().build();
    }

    @Bean("two")
    @ConfigurationProperties("spring.datasource.druid.two")
    public DataSource initSecondDataSource(){
        return DruidDataSourceBuilder.create().build();
    }

    @Bean
    @Primary
    public DynamicDataSource initDynamicDataSource(@Qualifier("one") DataSource ds1, @Qualifier("two") DataSource ds2){
        DynamicDataSource dynamicDataSource=new DynamicDataSource();

        Map<Object,Object> map=new HashMap<>();
        map.put(DataSource_Enum.one,ds1);
        map.put(DataSource_Enum.two,ds2);
        dynamicDataSource.setTargetDataSources(map);

        dynamicDataSource.setDefaultTargetDataSource(ds1);

        return dynamicDataSource;
    }

 

DataSource_Enum

public enum DataSource_Enum{
    one,two
}

 

*********************

aop 层

 

CustomAspect

@Aspect
@Component
public class CustomAspect {

    @Resource
    private DynamicDataSource dataSource;

    @Pointcut("execution(* *..UserMapper.*(..))")
    public void funOne(){
    }

    @Pointcut("execution(* *..PersonMapper.*(..))")
    public void funTwo(){
    }

    @Before("funOne()")
    public void beforeOne(){     //使用UserMapper时,使用数据库:one
        dataSource.switchDataSource(DataSource_Enum.one);
    }

    @Before("funTwo()")
    public void beforeTwo(){     //使用PersonMapper时,使用数据库:two
        dataSource.switchDataSource(DataSource_Enum.two);
    }
}

 

*********************

controller 层

 

UserController

@RestController
@RequestMapping("/user")
public class UserController {

    @Resource
    private UserMapper userMapper;

    @RequestMapping("/save")
    public String save(){
        for (int i=0;i<10;i++){
            User user=new User();
            user.setName("瓜田李下 "+i);
            user.setAge(i%5+10);

            userMapper.insert(user);
        }

        return "success";
    }
}

 

PersonController

@RestController
@RequestMapping("/person")
public class PersonController {

    @Resource
    private PersonMapper personMapper;

    @RequestMapping("/save")
    public String save(){
        for (int i=0;i<10;i++){
            Person person=new Person();
            person.setName("海贼王 "+i);
            person.setAge(i%4+12);

            personMapper.insert(person);
        }

        return "success";
    }
}

 

 

*********************

插入数据测试

 

表 user

              

 

表 person

              

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值