2013-12-16 23 views
1

我目前正在處理棘手的任務。列存儲索引更新使用表鎖定

背景:

  • 我有一個MSSQL數據庫2012多個表和一個巨大的行量 。由於在這個數據庫中搜索需要相當長的一段時間,我尋找改進查詢的方法。 (是的,我使用的索引, 已經看過執行計劃和這樣的東西:-)) 經過一番調查後,我發現在MSSQL 2012 企業的列存儲索引。這使我在搜索過程中獲得了巨大的性能提升。
  • 缺點:當指數啓用它不可能 INSERT/UPDATE/DELETE數據

目標:

  • 我想有可用的
  • 它的快速搜索應該可以一次運行多個工作者,以便INSERT/UPDATE/DELETE 數據(將工作分配給多個工作人員,訪問相同 個表)具有列存儲索引(通常在夜間進行)
  • 工人後已經完成了任務執行指標應該是 重建(和其他工人應該等到再)
  • 之後工作者應該繼續和禁用再次指標在那裏 是必要

目前的解決方案:

目前有到位的解決方案,但它不工作100%,因爲仍然是得到消息有時UPDATES和INSERTS不能執行,因爲應該先禁用列存儲索引(但它們應該根據我的操作),或者在存儲過程調用操作數據的過程中存在死鎖。

簡要概述我做了什麼。 我不確定是否使用列存儲索引更新表的最佳方法。 也讀了關於分區切換,但分區當前沒有使用(由於數據結構和搜索)

我在MSSQL數據庫中有以下存儲過程。

sp_columnstore_entity_disable(禁用表上的索引)

ALTER INDEX [ColumnStoreIndex_Entity] ON dbo.[Entity] DISABLE 

sp_columnstore_entity_rebuild(重建表上的索引)

ALTER INDEX [ColumnStoreIndex_Entity] ON dbo.[Entity] REBUILD 

sp_entity_insert_update工人長相

-- Whenever this stored procedure is executed index should be disabled in case it active 
EXEC sp_columnstore_entity_disable 

-- Insert or Update the entity 

程序代碼像這樣:

// get entities to process 
for(int i = 0; i < num_entities; i++) 
{ 
    // do some work 
    // insert/update entity 
} 

// Rebuild column store indexes again 
DBRebuildColumnStoreIndexes(); 

問題:

有時我接收到類似 事務(進程ID)的錯誤消息被死鎖的鎖資源與另一個過程和已被選作死鎖犧牲品 和我的進程崩潰。

有時我得到INSERT或UPDATE不可能的錯誤,因爲columnstore索引處於活動狀態。

我已經想過表鎖在重建和修改過程中不會遇到競爭狀態。

我很高興任何建議或幫助解決問題

+0

你確實意識到幾百個演出的桌子上,你會在重建期間完全鎖定桌子?你爲什麼想做這個? – Namphibian

+0

是的,我意識到這一點。如果有更好的方法,我可以保持這種快速搜索,並且一次對多個工作人員進行數據操作,請讓我知道。 :)數據操作目前在一夜之間完成,所以它不會影響正常的工作時間。 – Anubis

+1

如果數據操作全部都是在一夜之間完成的,如果在開始任何數據操作(對於任何工作人員)之前刪除列存儲索引,並且在完成所有數據操作(針對所有工作人員)後重建它,是否可以接受?而不是爲每個工人做。 –

回答

0

在我的舊的團隊,我們正在考慮的列存儲索引功能,我們將要執行的數據倉庫任務我們的歸檔記錄,但數據庫是一個高度事務性的數據庫,需要24/7的正常運行時間。我們的解決方案是建立一個ETL過程,將數據轉儲到一個單獨的數據倉庫數據庫中,我們啓用了列存儲索引。也就是說,我們使用了2014年並啓用了集羣式列存儲索引,它允許插入/更新/刪除,但允許在單獨的表中允許表和索引的維護任務,而不影響操作。

根據我的經驗,最好有專門的操作數據庫和單獨的報告數據庫。特別是如果在操作上,您可以歸檔大量您希望保留用於報告的記錄。