SSM框架多数据源AOP注解方式实现

一、jdbc.properties文件

jdbc.driver=oracle.jdbc.driver.OracleDriver

jdbc1.url=jdbc\:oracle\:thin\:@xxx.xxx.xxx.xxx\:1521\:xxx
jdbc1.username=xxx
jdbc1.password=xxx

jdbc2.url=jdbc\:oracle\:thin\:@xxx.xxx.xxx.xxx\:1521\:xxx
jdbc2.username=xxx
jdbc2.password=xxx

validationQuery=select 1 from dual

二、Spring-mybatis.xml文件

<!-- 引入配置文件 -->
<context:property-placeholder location="classpath:properties/*.properties" ignore-unresolvable="true" />

<!-- 数据源1 -->
<bean id="dataSource1" class="com.alibaba.druid.pool.DruidDataSource"
destroy-method="close">
<property name="url" value="${jdbc1.url}" />
<property name="username" value="${jdbc1.username}" />
<property name="password" value="${jdbc1.password}" />
<property name="driverClassName" value="${jdbc.driver}" />
<property name="initialSize" value="0" />
<property name="maxActive" value="20" />
<property name="maxIdle" value="20" />
<property name="minIdle" value="0" />
<property name="maxWait" value="60000" />
<property name="validationQuery" value="${validationQuery}" />
<property name="testOnBorrow" value="false" />
<property name="testOnReturn" value="false" />
<property name="testWhileIdle" value="true" />
<property name="timeBetweenEvictionRunsMillis" value="60000" />
<property name="minEvictableIdleTimeMillis" value="25200000" />
<property name="removeAbandoned" value="true" />
<property name="removeAbandonedTimeout" value="1800" />
<property name="logAbandoned" value="true" />
<property name="filters" value="mergeStat" />
</bean>

<!--数据源2-->
<bean id="dataSource2" class="com.alibaba.druid.pool.DruidDataSource"
destroy-method="close">
<property name="driverClassName" value="${jdbc.driver}" />
<property name="url" value="${jdbc2.url}" />
<property name="username" value="${jdbc2.username}" />
<property name="password" value="${jdbc2.password}" />

<property name="initialSize" value="0" />
<property name="maxActive" value="20" />
<property name="maxIdle" value="20" />
<property name="minIdle" value="0" />
<property name="maxWait" value="60000" />
<property name="validationQuery" value="${validationQuery}" />
<property name="testOnBorrow" value="false" />
<property name="testOnReturn" value="false" />
<property name="testWhileIdle" value="true" />
<property name="timeBetweenEvictionRunsMillis" value="60000" />
<property name="minEvictableIdleTimeMillis" value="25200000" />
<property name="removeAbandoned" value="true" />
<property name="removeAbandonedTimeout" value="1800" />
<property name="logAbandoned" value="true" />
<property name="filters" value="mergeStat" />
</bean>

<!-- 自定义数据源切换类 -->
<bean id="dynamicDataSource" class="gateway.common.DynamicDataSource">
<!-- 这里可以指定默认的数据源 -->
<property name="defaultTargetDataSource" ref="dataSource2" />
<property name="targetDataSources">
<map key-type="java.lang.String">
<!-- 指定lookupKey和与之对应的数据源 -->
<entry key="dataSource1" value-ref="dataSource1"></entry>
<entry key="dataSource2" value-ref="dataSource2"></entry>
</map>
</property>
</bean>

<!-- MyBatis SqlSessionFactoryBean 配置 -->
<bean id="sqlSessionFactory"
class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dynamicDataSource" />
<property name="configLocation" value="classpath:xml/mybatis-config.xml" />
<property name="typeAliasesPackage" value="gateway.entity" />
<property name="mapperLocations" value="classpath:mapper/*Mapper.xml" />
</bean>

<!-- 扫描dao -->
<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
<property name="basePackage" value="gateway.dao" />
</bean>

<!-- 事务管理器 -->
<bean id="transactionManager"
class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<!-- 数据源 -->
<property name="dataSource" ref="dynamicDataSource" />
</bean>


<!-- 映射接口 -->
<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
<property name="basePackage" value="com.baimi.routerweb.mapper"></property>
</bean>


<!-- 通知 -->
<tx:advice id="txAdvice" transaction-manager="transactionManager">
<tx:attributes>
<!-- 传播行为 -->
<tx:method name="save*" propagation="REQUIRED" />
<tx:method name="insert*" propagation="REQUIRED" />
<tx:method name="add*" propagation="REQUIRED" />
<tx:method name="create*" propagation="REQUIRED" />
<tx:method name="delete*" propagation="REQUIRED" />
<tx:method name="update*" propagation="REQUIRED" />
<tx:method name="find*" propagation="SUPPORTS" read-only="true" />
<tx:method name="select*" propagation="SUPPORTS" read-only="true" />
<tx:method name="get*" propagation="SUPPORTS" read-only="true" />
</tx:attributes>
</tx:advice>
<!-- 切面 -->
<aop:config> <aop:advisor advice-ref="txAdvice" pointcut="execution(* gateway.service.impl.*.*(..))" /> </aop:config> 

三、自定义数据源选择器类

package gateway.common;
import org.springframework.jdbc.datasource.lookup.AbstractRoutingDataSource;

public class DynamicDataSource extends AbstractRoutingDataSource {
private static final ThreadLocal<String> dataSourceKey = new InheritableThreadLocal<String>();

public static void setDataSourceKey(String dataSource){
dataSourceKey.set(dataSource);
}


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


四、自定义注解

package gateway.common;


import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;


/**
  * 定义DataSource的注解
  */


@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.METHOD,ElementType.TYPE})
@Documented
public @interface DataSwitch {
String dataSource() default "";
}

五、前置通知(我这里切的是controller,切哪自定义,改一下包名就OK)

@Aspect
public class LogAopAction {

//配置接入点
@Pointcut("execution(* gateway.web.controller..*.*(..))")  
private void controllerAspect(){}//定义一个切入点


@Before("controllerAspect()")
public void dataSwitch(JoinPoint joinPoint){
Signature signature = joinPoint.getSignature();
MethodSignature methodSignature =(MethodSignature) signature;
Method method = methodSignature.getMethod();
DataSwitch data = null;
String dataSource = "";
if(method != null){
data = method.getAnnotation(DataSwitch.class);
if(data != null){
dataSource = data.dataSource();
if(dataSource != null){
DynamicDataSource.setDataSourceKey(dataSource);
}
}
}
}
}

六、Spring-mvc中添加aop配置

<!-- 开启aop,对类代理 -->
<aop:aspectj-autoproxy proxy-target-class="true" />
<bean id="logAopAction" class="com.datacvg.zx.aspectj.LogAopAction"/>

七、在需要切换数据源的controller方法上添加自定义注解

@DataSwitch(dataSource="dataSource1")




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值