springmvc+mybatis 配置多資料來源相互切換
阿新 • • 發佈:2019-01-31
近日因為專案需求,需要動態切換資料來源,就稍稍做了下研究,理解的不深,有不對的地方還望高人指點。
直接貼上程式碼:
resource.xml
<bean id="sqlSessionFactory" class="com.hotent.core.mybatis.SqlSessionFactoryFactoryBean"> <property name="configLocation" value="classpath:/conf/configuration.xml"/> <property name="mapperLocations" > <list> <value>classpath:/com/hotent/*/maper/*.map.xml</value> </list> </property> <property name="dataSource" ref="dataSource"/> </bean> <bean id="dataSource" class="com.hotent.core.db.DynamicDataSource"> <property name="targetDataSources"> <map key-type="java.lang.String"> <entry key="dataSourceOrg" value-ref="dataSourceOrg" /> <entry key="defaultDataSource" value-ref="defaultDataSource" /> </map> </property> <property name="defaultTargetDataSource" ref="defaultDataSource" /> </bean> <bean id="dataSourceOrg" class="com.alibaba.druid.pool.DruidDataSource" init-method="init" destroy-method="close" > <property name="driverClassName" value="${jdbc.driverClassNameOrg}"/> <property name="url" value="${jdbc.urlOrg}"/> <property name="username" value="${jdbc.usernameOrg}"/> <property name="password" value="${jdbc.passwordOrg}"/> </bean> <bean id="defaultDataSource" class="com.alibaba.druid.pool.DruidDataSource" init-method="init" destroy-method="close" > <property name="driverClassName" value="${jdbc.driverClassName}"/> <property name="url" value="${jdbc.url}"/> <property name="username" value="${jdbc.username}"/> <property name="password" value="${jdbc.password}"/> </bean> <pre name="code" class="plain">
我這裡配置資料庫連線池用的是 com.alibaba.druid.pool.DruidDataSource 。下面的DynamicDataSource是實現AbstractRoutingDataSource 的 。
public class DynamicDataSource extends AbstractRoutingDataSource { /** * 取得當前使用那個資料來源。 */ @Override protected Object determineCurrentLookupKey() { return DbContextHolder.getDbType(); } @Override public Logger getParentLogger() throws SQLFeatureNotSupportedException { // TODO Auto-generated method stub return null; } //設定資料來源集合. @Override public void setTargetDataSources(Map targetDataSources) { super.setTargetDataSources(targetDataSources); } }
DbContextHolder.java
這裡兩個常量就是兩個資料來源的id.以後增加資料來源,這裡也要增加。setDbType就用做後面切換資料時候設定當前資料來源。當完成操作以後要呼叫clearDbType方法恢復預設資料來源。public class DbContextHolder { private static final ThreadLocal<String> contextHolder = new ThreadLocal<String>(); public static final String DATA_SOURCE_DEFAULT = "defaultDataSource"; public static final String DATA_SOURCE_ORG = "dataSourceOrg"; /** * 設定當前資料庫。 * @param dbType */ /* @Resource private DynamicDataSource dds;*/ public static void setDbType(String dbType) { contextHolder.set(dbType); } /** * 取得當前資料來源。 * @return */ public static String getDbType() { String str = (String) contextHolder.get(); if (null == str || "".equals(str)) str = "1"; return str; } /** * 清除上下文資料 */ public static void clearDbType() { contextHolder.remove(); } }
test.java
public class test {
@Test
public void test() {
ApplicationContext cxt = new ClassPathXmlApplicationContext(new String[] {"conf/app-context.xml"});
IAuthenticate service = (IAuthenticate)cxt.getBean("iAuthenticate");
SysOrg org = new SysOrg();
org.setOrgId(123456789L);
org.setOrgName("測試資料來源");
org.setAreaid(1L);
//service.add(org);
List<ISysOrg> sysorg_ =service.getAllOrgs();
JSONArray json =JSONArray.fromObject(sysorg_);
System.out.println(json.toString());
DbContextHolder.setDbType(DbContextHolder.DATA_SOURCE_ORG);//切換資料來源
List<ISysOrg> sysorg_1 =service.getAllOrgs();
JSONArray json1 =JSONArray.fromObject(sysorg_1);
System.out.println(json1.toString());
DbContextHolder.clearDbType();//恢復預設資料來源
}
}
執行,切換成功。
中間遇到過一個問題,一直沒有解決,還不知道是為什麼,我用org.logicalcobwebs.proxool.ProxoolDataSource配置資料庫連線池的時候資料來源無法切換,後來改成com.alibaba.druid.pool.DruidDataSource、com.hotent.core.db.DynamicDataSource都可以。暫時還沒查到原因。還望高人指點一下。