SSM配置多数据源

第一种方法:使用工具类

配置properties文件

#-----------------oracle 第一个数据源-------------
datesources.driverClass=oracle.jdbc.driver.OracleDriver
datesources.jdbcUrl=jdbc\:oracle\:thin\:@localhost\:1521\:orcl
datesources.user=test
datesources.password=test
#-----------------oracle 第二个数据源-------------
datesources2.driverClass=oracle.jdbc.driver.OracleDriver
datesources2.jdbcUrl=jdbc\:oracle\:thin\:@localhost\:1521\:orcl
datesources2.user=tjsfjd
datesources2.password=tjsfjd

配置applicationContext.xml文件

<!--dbcp是apache的链接池-->
    <!--org.springframework.jdbc.datasource.DriverManagerDataSource使用传统的jdbc链接方式-->
    <!--第一个数据源-->
    <bean id="dataSource1" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close">
        <property name="driverClassName" value="${datesources.driverClass}"></property>
        <property name="url" value="${datesources.jdbcUrl}"></property>
        <property name="username" value="${datesources.user}"></property>
        <property name="password" value="${datesources.password}"></property>
    </bean>
    <!--第二个数据源-->
    <bean id="dataSource2" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close">
        <property name="driverClassName" value="${datesources2.driverClass}"></property>
        <property name="url" value="${datesources2.jdbcUrl}"></property>
        <property name="username" value="${datesources2.user}"></property>
        <property name="password" value="${datesources2.password}"></property>
    </bean>
    <!--com.my.ssmmaven.util.DataSources 为获取获取数据源类-->
    <bean id="dataSource" class="com.my.ssmmaven.util.DataSources">
             <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>
           <!-- 这里可以指定默认的数据源 -->
            <property name="defaultTargetDataSource" ref="dataSource1" />
    </bean>

编码工具类

1.DataSources

2.DynamicDataSourceHolder

package com.my.ssmmaven.util;

/**
 * @author zhoujq
 * @version 1.0
 * @description
 * @date 2018/7/12 19:55
 * @modified
 */
public class DynamicDataSourceHolder {
    /**
     * 注意:数据源标识保存在线程变量中,避免多线程操作数据源时互相干扰
     */
    private static final ThreadLocal<String> THREAD_DATA_SOURCE = new ThreadLocal<String>();

    public static String getDataSource() {
        return THREAD_DATA_SOURCE.get();
    }

    /**
     * 切换数据源
     * @param dataSource 数据源
     */
    public static void setDataSource(String dataSource) {
        THREAD_DATA_SOURCE.set(dataSource);
    }

    public static void clearDataSource() {
        THREAD_DATA_SOURCE.remove();
    }
}

 

package com.my.ssmmaven.util;

import org.springframework.jdbc.datasource.lookup.AbstractRoutingDataSource;

/**
 * @author zhoujq
 * @version 1.0
 * @description ssm配置多个数据源
 * @date 2018/7/12 19:43
 * @modified
 */
public class DataSources extends AbstractRoutingDataSource {

    @Override
    protected Object determineCurrentLookupKey() {
        // 从自定义的位置获取数据源标识
        return DynamicDataSourceHolder.getDataSource();
    }
}

service层调用

package com.my.ssmmaven.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.github.pagehelper.PageInfo;
import com.my.ssmmaven.mapper.IGetTestListMapper;
import com.my.ssmmaven.service.IGetTestListService;
import com.my.ssmmaven.util.DataSources.DataSourcesMenu;
import com.my.ssmmaven.util.DataSources.DynamicDataSourceHolder;
import com.my.ssmmaven.util.TurnPage;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.List;

/**
 * @author zhoujq
 * @version 1.0
 * @description
 * @date 2018/7/6 10:52
 * @modified
 */
@Service
public class GetTestListServerImpl implements IGetTestListService{

    @Resource
    IGetTestListMapper getTestListMapper;

    /**
     * 使用默认数据源
     * @param params
     * @return
     */
    @Override
    public JSONObject getTestList(JSONObject params) {
        JSONObject result = new JSONObject();
        List<JSONObject> list= getTestListMapper.getTestList(params);
        result.put("list",list);
        return result;
    }

    /**
     * 使用第二个数据源
     * @return
     */
    @Override
    public JSONObject getOrgList() {
        DynamicDataSourceHolder.setDataSource(DataSourcesMenu.TJSFJD.getValue());
        JSONObject result = new JSONObject();
        List<JSONObject> list= getTestListMapper.getOrgList();
        result.put("list",list.get(0));
        return result;
    }
}

第二种方法:使用注解

配置pom.xml,引入依赖

 <dependency>
            <groupId>org.aspectj</groupId>
            <artifactId>aspectjrt</artifactId>
            <version>1.6.11</version>
        </dependency>

        <dependency>
            <groupId>org.aspectj</groupId>
            <artifactId>aspectjweaver</artifactId>
            <version>1.6.11</version>
  </dependency>

配置applicationContext.xml

1.配置数据源 (省略)

2.配置注解拦截器,aop注入

 <!--配置注解aop及拦截器     class 全类名 -->
    <bean id="dataSourceAspect" class="com.my.ssmmaven.util.AnoDataSources.DataSourceAspect"/>
    <aop:config>
        <aop:aspect ref="dataSourceAspect">
            <!-- 拦截所有service方法 -->
            <aop:pointcut id="dataSourcePointcut" expression="execution(* com.my.ssmmaven.service.*.*(..))"/>
            <aop:before pointcut-ref="dataSourcePointcut" method="intercept"/>
        </aop:aspect>
    </aop:config>

编写工具类

1.DataSource

2.DataSourceAspect

package com.my.ssmmaven.util.AnoDataSources;

import java.lang.annotation.Retention;
import java.lang.annotation.Target;
import static java.lang.annotation.ElementType.METHOD;
import static java.lang.annotation.ElementType.TYPE;
import static java.lang.annotation.RetentionPolicy.RUNTIME;

@Target({ TYPE, METHOD })
@Retention(RUNTIME)
public @interface DataSource {
    String value();
}
package com.my.ssmmaven.util.AnoDataSources;

import com.my.ssmmaven.util.DataSources.DynamicDataSourceHolder;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.reflect.MethodSignature;

import java.lang.reflect.Method;


/**
 * @author zhoujq
 * @version .
 * @description
 * @date // :
 * @modified
 */
public class DataSourceAspect {
    /**
           * 拦截目标方法,获取由@DataSource指定的数据源标识,设置到线程存储中以便切换数据源
           *
           * @param point
           * @throws Exception
           */
      public void intercept(JoinPoint point) throws Exception {
                 Class<?> target = point.getTarget().getClass();
                 MethodSignature signature = (MethodSignature) point.getSignature();
                 // 默认使用目标类型的注解,如果没有则使用其实现接口的注解
                 for (Class<?> clazz : target.getInterfaces()) {
                         resolveDataSource(clazz, signature.getMethod());
                     }
                 resolveDataSource(target, signature.getMethod());
             }

             /**
       * 提取目标对象方法注解和类型注解中的数据源标识
       *
       * @param clazz
       * @param method
       */
             private void resolveDataSource(Class<?> clazz, Method method) {
                 try {
                         Class<?>[] types = method.getParameterTypes();
                         // 默认使用类型注解
                         if (clazz.isAnnotationPresent(DataSource.class)) {
                                 DataSource source = clazz.getAnnotation(DataSource.class);
                                 DynamicDataSourceHolder.setDataSource(source.value());
                             }
                         // 方法注解可以覆盖类型注解
                         Method m = clazz.getMethod(method.getName(), types);
                         if (m != null && m.isAnnotationPresent(DataSource.class)) {
                                 DataSource source = m.getAnnotation(DataSource.class);
                                 DynamicDataSourceHolder.setDataSource(source.value());
                             }
                     } catch (Exception e) {
                         System.out.println(clazz + ":" + e.getMessage());
                     }
             }

}

 

service层调用,可在方法名或者类名上使用注解

 

package com.my.ssmmaven.service.impl;

import com.alibaba.fastjson.JSONObject;
import com.my.ssmmaven.mapper.IGetTestListMapper;
import com.my.ssmmaven.service.IGetTestListService;
import com.my.ssmmaven.util.AnoDataSources.DataSource;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.List;

/**
 * @author zhoujq
 * @version 1.0
 * @description
 * @date 2018/7/6 10:52
 * @modified
 */
@Service
public class GetTestListServerImpl implements IGetTestListService{

    @Resource
    IGetTestListMapper getTestListMapper;

    /**
     * 使用默认数据源
     * @param params
     * @return
     */
    @Override
    @Transactional
    public JSONObject getTestList(JSONObject params) {
        JSONObject result = new JSONObject();
        List<JSONObject> list= getTestListMapper.getTestList(params);
        result.put("list",list);
        return result;
    }

    /**
     * 使用第二个数据源
     * @return
     */
    @Override
    @DataSource("dataSource2")
    public JSONObject getOrgList() {
        JSONObject result = new JSONObject();
        List<JSONObject> list= getTestListMapper.getOrgList();
        result.put("list",list.get(0));
        return result;
    }
}

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值