一区二区三区在线-一区二区三区亚洲视频-一区二区三区亚洲-一区二区三区午夜-一区二区三区四区在线视频-一区二区三区四区在线免费观看

服務器之家:專注于服務器技術及軟件下載分享
分類導航

PHP教程|ASP.NET教程|Java教程|ASP教程|編程技術|正則表達式|C/C++|IOS|C#|Swift|Android|VB|R語言|JavaScript|易語言|vb.net|

服務器之家 - 編程語言 - Java教程 - Spring實現動態切換多數據源的解決方案

Spring實現動態切換多數據源的解決方案

2020-07-27 14:34nevergiveupzeng Java教程

這篇文章主要給大家介紹了Spring實現動態切換多數據源的解決方案,文中給出了詳細的介紹和示例代碼,相信對大家的理解和學習具有一定的參考借鑒價值,有需要的朋友可以參考學習,下面來一起看看吧。

前言

Spring動態配置多數據源,即在大型應用中對數據進行切分,并且采用多個數據庫實例進行管理,這樣可以有效提高系統的水平伸縮性。而這樣的方案就會不同于常見的單一數據實例的方案,這就要程序在運行時根據當時的請求及系統狀態來動態的決定將數據存儲在哪個數據庫實例中,以及從哪個數據庫提取數據。

Spring2.x以后的版本中采用Proxy模式,就是我們在方案中實現一個虛擬的數據源,并且用它來封裝數據源選擇邏輯,這樣就可以有效地將數據源選擇邏輯從Client中分離出來。Client提供選擇所需的上下文(因為這是Client所知道的),由虛擬的DataSource根據Client提供的上下文來實現數據源的選擇。

實現

具體的實現就是,虛擬的DataSource僅需繼承AbstractRoutingDataSource實現determineCurrentLookupKey()在其中封裝數據源的選擇邏輯。

一、動態配置多數據源

1. 數據源的名稱常量類:

?
1
2
3
4
5
6
7
8
9
10
/**
 * 動態配置多數據源
 * 數據源的名稱常量類
 * @author LONGHUI_LUO
 *
 */
public class DataSourceConst {
 public static final String TEST="test";
 public static final String USER="User";
}

2. 建立一個獲得和設置上下文環境的類,主要負責改變上下文數據源的名稱:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
/**
 * 獲得和設置上下文環境 主要負責改變上下文數據源的名稱
 *
 * @author LONGHUI_LUO
 *
 */
public class DataSourceContextHolder {
 private static final ThreadLocal contextHolder = new ThreadLocal(); // 線程本地環境
 
 // 設置數據源類型
 public static void setDataSourceType(String dataSourceType) {
  contextHolder.set(dataSourceType);
 }
 
 // 獲取數據源類型
 public static String getDataSourceType() {
  return (String) contextHolder.get();
 }
 
 // 清除數據源類型
 public static void clearDataSourceType() {
  contextHolder.remove();
 }
 
}

3. 建立動態數據源類,注意,這個類必須繼承AbstractRoutingDataSource,且實現方法determineCurrentLookupKey,該方法返回一個Object,一般是返回字符串:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
/**
 * 建立動態數據源
 *
 * @author LONGHUI_LUO
 *
 */
public class DynamicDataSource extends AbstractRoutingDataSource {
 
 protected Object determineCurrentLookupKey() {
 // 在進行DAO操作前,通過上下文環境變量,獲得數據源的類型
 return DataSourceContextHolder.getDataSourceType();
 }
 
}

4. 編寫spring的配置文件配置多個數據源

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
  <!-- 數據源相同的內容 -->
<bean
  id="parentDataSource"
  class="org.apache.commons.dbcp.BasicDataSource"
  destroy-method="close">
  <property
   name="driverClassName"
   value="com.microsoft.sqlserver.jdbc.SQLServerDriver" />
  <property name="username" value="sa" />
  <property name="password" value="net2com" />
</bean>
<!-- start以下配置各個數據源的特性 -->
<bean parent="parentDataSource" id="testDataSource">
  <propertynamepropertyname="url" value="jdbc:sqlserver://localhost:1433;databaseName=test" />
</bean>
<bean parent="parentDataSource" id="UserDataSource">
   <property
   name="url"
   value="jdbc:sqlserver://localhost:1433;databaseName=User" />
</bean>
<!-- end 配置各個數據源的特性 -->

5. 編寫spring配置文件配置多數據源映射關系

?
1
2
3
4
5
6
7
8
9
<bean class="com.xxxx.datasouce.DynamicDataSource" id="dataSource">
 <property name="targetDataSources">
  <map key-type="java.lang.String">
   <entry value-ref="testDataSource" key="test"></entry>
   <entry value-ref="UserDataSource" key="User"></entry>
  </map>
 </property>
 <property name="defaultTargetDataSource" ref="testDataSource" ></property>
</bean>

在這個配置中第一個property屬性配置目標數據源,<map key-type="java.lang.String">中的key-type必須要和靜態鍵值對照類DataSourceConst中的值的類型相 同;<entry key="User" value-ref="userDataSource"/>中key的值必須要和靜態鍵值對照類中的值相同,如果有多個值,可以配置多個< entry>標簽。第二個property屬性配置默認的數據源。

動態切換是數據源

?
1
DataSourceContextHolder.setDataSourceType(DataSourceConst.TEST);

該方案的優勢

首先,這個方案完全是在spring的框架下解決的,數據源依然配置在spring的配置文件中,sessionFactory依然去配置它的dataSource屬性,它甚至都不知道dataSource的改變。唯一不同的是在真正的dataSource與sessionFactory之間增加了一個MultiDataSource。

其次,實現簡單,易于維護。這個方案雖然我說了這么多東西,其實都是分析,真正需要我們寫的代碼就只有MultiDataSource、SpObserver兩個類。MultiDataSource類真正要寫的只有getDataSource()getDataSource(sp)兩個方法,而SpObserver類更簡單了。實現越簡單,出錯的可能就越小,維護性就越高。

最后,這個方案可以使單數據源與多數據源兼容。這個方案完全不影響BUS和DAO的編寫。如果我們的項目在開始之初是單數據源的情況下開發,隨著項目的進行,需要變更為多數據源,則只需要修改spring配置,并少量修改MVC層以便在請求中寫入需要的數據源名,變更就完成了。如果我們的項目希望改回單數據源,則只需要簡單修改配置文件。這樣,為我們的項目將增加更多的彈性。

該方案的缺點

沒有能夠解決多用戶訪問單例“sessionFactory”時共享“dataSource”變量,導致產生爭搶“dataSource”的結果,本質類似于操作系統中的“生產者消費者”問題。因此當多用戶訪問時,多數據源可能會導致系統性能下降的后果。

總結

以上就是這篇文章的全部內容了,希望本文的內容對大家的學習或者工作能帶來一定的幫助,如果有疑問大家可以留言交流。

原文鏈接:http://www.cnblogs.com/zengda/p/4500684.html?utm_source=tuicool

延伸 · 閱讀

精彩推薦
主站蜘蛛池模板: 网红思瑞一区二区三区 | 久草在线精彩免费视频 | 婷婷在线成人免费观看搜索 | 天天色综| 毛片视频网站 | 蜜桃影像传媒破解版 | 青青视频国产依人在线 | 国产欧美综合精品一区二区 | 日产精品一卡2卡三卡4乱码久久 | 国产成人在线视频 | 无人区尖叫之夜美女姐姐视频 | 精品日韩视频 | 爆操俄罗斯美女 | 国产小嫩模好紧 | 免费午夜影院 | 草莓丝瓜芭乐樱桃榴莲色多黄 | 99ri国产精品 | 男同gay作爰视频网站 | 日韩aaa| 和老外3p爽粗大免费视频 | 国产在线乱子伦一区二区 | 好姑娘完整版在线观看中文 | 大胆国模一区二区三区伊人 | 国产精品一级视频 | 好大好硬好紧太深了受不了 | 国产美女操 | 无遮掩60分钟从头啪到尾 | 日韩国产成人资源精品视频 | 国产成人综合久久 | 国产成人一区二区三区在线视频 | 四虎在线永久免费视频网站 | 狠狠色96视频 | 日韩欧美一区二区三区中文精品 | 成年人视频在线播放 | 校花小雪灌满了男人们的浓浆 | 17岁俄罗斯csgo| 十大免费批日的软件 | 国产欧美精品一区二区三区–老狼 | 金莲一级淫片aaaaaa | 九色PORNY真实丨国产大胸 | 香蕉免费看一区二区三区 |