以前寫過一篇博客「SQL Server中是否能夠準確獲取最後一次索引重建的時間?「,裏面主要講述了三個問題:咱們可否找到索引的建立時間?最後一次索引重建(Index Rebuild)的時間? 最後一次索引重組(INDEX REORGANIZE)的時間呢?,當時得出的結論,答案是咱們沒法準確的找到索引的建立時間、最後一次索引重組時間,最後一次索引重建的時間。可是最近看到一篇博客「SQL Server – Get Index Creation Date」,而後研究了一下,即便SQL Server暫時沒有一個系統表或DMV視圖有保存索引建立的時間,索引重建的時間、索引重組的時間。可是咱們能夠經過系統跟蹤文件獲取它們的值,固然也有限制條件,並非全部的索引都能找到這些值。請見下面詳細解說:html
索引的建立時間sql
索引的建立時間,能夠用下面SQL獲取,可是咱們知道跟蹤有可能中止或禁用;跟蹤文件也可能被覆蓋。因此這種方法只能查詢最近一段時間的。它有很強的時效性。因此這種方法不能通用。註定其只能做爲一種方法參考,而不能通用。app
DECLARE @filename VARCHAR(500)
SELECT @filename = CAST(value AS VARCHAR(500))
FROM fn_trace_getinfo(DEFAULT)
WHERE property = 2
AND value IS NOT NULL
-- Go back 4 files since default trace only keeps the last 5 and start from there.
SELECT @filename = substring(@filename, 0, charindex('_', @filename)+1) + convert(varchar, (convert(int, substring(left(@filename, len(@filename)-4), charindex('_', @filename)+1, len(@filename)))-4)) + '.trc'
SELECT
gt.EventClass,
gt.EventSubClass,
te.Name AS EventName,
gt.HostName,
gt.StartTime,
gt.DatabaseName,
gt.ObjectName,
gt.IndexID
FROM fn_trace_gettable(@fileName, DEFAULT) gt
JOIN sys.trace_events te ON gt.EventClass = te.trace_event_id
WHERE EventClass = 46
and ObjectType = 22601
and gt.DatabaseName <> 'tempdb'
ORDER BY StartTime desc;
索引的重建時間 &索引的重組時間測試
以下所示,Object:Altered的trace_event_id爲164,這裏咱們沒法區分ALTER INDEX ... REBUILD 和 ALETER INDEX ...REORGANIZE. 對於索引重建、索引重組,fn_trace_gettable返回的TextData爲Null值,也無從判斷。因此這裏能記錄準確的時間,可是沒法區分索引重建與索引重組。ui
DECLARE @filename VARCHAR(500)
SELECT @filename = CAST(value AS VARCHAR(500))
FROM fn_trace_getinfo(DEFAULT)
WHERE property = 2
AND value IS NOT NULL
-- Go back 4 files since default trace only keeps the last 5 and start from there.
SELECT @filename = substring(@filename, 0, charindex('_', @filename)+1) + convert(varchar, (convert(int, substring(left(@filename, len(@filename)-4), charindex('_', @filename)+1, len(@filename)))-4)) + '.trc'
SELECT
gt.EventClass,
gt.EventSubClass,
te.Name AS EventName,
gt.HostName,
gt.StartTime,
gt.DatabaseName,
gt.ObjectName,
gt.IndexID
FROM fn_trace_gettable(@fileName, DEFAULT) gt
JOIN sys.trace_events te ON gt.EventClass = te.trace_event_id
WHERE EventClass = 164
and ObjectType = 22601
and gt.DatabaseName <> 'tempdb'
ORDER BY StartTime desc;
測試驗證以下所示:spa
USE YourSQLDba;
GO
ALTER INDEX Pk_HistMaintTrav ON [Maint].[JobHistory] REBUILD;
ALTER INDEX PK_DataBaseSizeDtl_Day ON [Maint].[DataBaseSizeDtl_Day] REORGANIZE;
CREATE INDEX IX_DataBaseSizeDtl_Day_N1 ON [Maint].[DataBaseSizeDtl_Day](DataBaseName);
注意:上面腳本在有些環境可能會出錯,主要是由於trac文件的路徑,例如C:\Program Files\Microsoft SQL Server\MSSQL10_50.MSSQLSERVER\MSSQL\Log\log_603.trc 就會遇到下面錯誤,須要根據實際狀況修改腳本。code
Msg 245, Level 16, State 1, Line 8orm
Conversion failed when converting the varchar value '50.MSSQLSERVER\MSSQL\Log\log_603' to data type int.server
參考資料:htm
https://sqlconjuror.com/sql-server-get-index-creation-date/