2008-11-03 142 views
62

sql2k8中的活動監視器允許我們查看最昂貴的查詢。好的,這很酷,但有沒有辦法記錄這些信息或通過查詢分析器獲取這些信息?我並不想讓Sql管理控制檯處於打開狀態,並且我正在查看活動監視器儀表板。如何登錄並查找最昂貴的查詢?

我想弄清楚哪些查詢寫得不好/架構設計不良等

任何幫助,感謝堆!

回答

60
  1. 使用SQL Server Profiler(SSMS中的工具菜單上)來創建記錄這些事件跡:

    RPC:Completed 
    SP:Completed 
    SP:StmtCompleted 
    SQL:BatchCompleted 
    SQL:StmtCompleted 
    
  2. 您可以用標準的跟蹤模板開始和修剪它。您沒有指定這是針對特定數據庫還是針對整個服務器,如果針對特定數據庫,包含DatabaseID列並將篩選器設置爲您的數據庫(SELECT DB_ID('dbname'))。確保每個事件都包含邏輯讀取數據列。將跟蹤設置爲登錄到文件。如果您將此跟蹤放在後臺無人值守運行,那麼設置最大跟蹤文件大小(如500兆或1GB)是一個好主意(如果您有足夠的空間)(這完全取決於服務器上有多少活動,所以你將不得不吮吸它並看到)。

  3. 簡要地開始跟蹤,然後暫停它。轉到文件 - >導出 - >腳本跟蹤定義並選擇您的數據庫版本,並保存到文件。你現在有了一個sql腳本來創建一個比通過profiler GUI運行更少的開銷。當你運行這個腳本時,它會輸出Trace ID(通常爲@ID=2);注意這一點。

  4. 一旦你有一個跟蹤文件(帶.trc)(無論是跟蹤完成後,由於達到最大文件大小,或者您已停止使用

    EXEC sp_trace_setstatus @ID運行跟蹤,0
    EXEC sp_trace_setstatus @ID ,2

您可以跟蹤加載到事件探查器,或使用ClearTrace(很方便),或者將其加載到一個表像這樣:

SELECT * INTO TraceTable 
FROM ::fn_trace_gettable('C:\location of your trace output.trc', default) 

然後你可以運行一個查詢來彙總數據,比如這一個:

SELECT COUNT(*) AS TotalExecutions, 
    EventClass, CAST(TextData as nvarchar(2000)) 
,SUM(Duration) AS DurationTotal 
,SUM(CPU) AS CPUTotal 
,SUM(Reads) AS ReadsTotal 
,SUM(Writes) AS WritesTotal 
FROM TraceTable 
GROUP BY EventClass, CAST(TextData as nvarchar(2000)) 
ORDER BY ReadsTotal DESC 

一旦你已經確定了昂貴的疑問,您可以生成並檢查實際執行計劃。

+0

歡呼聲mitch!聽起來有點複雜,我認爲是必需的,但我絕對會放棄它:)乾杯! – 2008-11-03 04:46:29

+0

平淡無奇 - 我期待着有機會走向新世界的盡頭......然後我會標記問題或詢問更多問題。 – 2008-11-15 06:11:07

2

SQL Server Profiler會執行您所需的操作嗎?我還沒有使用2008年,所以我不知道該工具是否仍在那裏,但如果是這樣的話,我相信你可以設置一個跟蹤來記錄符合特定標準的查詢(例如那些執行和驅動CPU以上的查詢一定的門檻)。

我們已經在我們的項目中使用了它,它在幫助我們解決執行不佳的查詢(儘管不要全天放置它,依靠一般的Windows性能計數器進行性能健康跟蹤)方面做了很好的工作。

+0

嗯..我已經使用了剖析器堆,但沒有總結信息。它是每個查詢類型的東西的一條線。 – 2008-11-03 04:30:53

4

我以前從來沒有聽說過這個工具,但是微軟提供了一套報告,可以爲您提供完美的報告 - 包括最慢的查詢。看看他們的Performance Dashboard Reports

不確定它們是否與SQL 2008兼容,但值得檢查。

2

SQL Server 2008中有一個新工具,Performance Studio,它建立在服務器自動維護的動態管理視圖的基礎之上,該視圖給出了服務器性能的概述。值得檢查。

20

以下腳本爲您提供結果。

SELECT TOP 10 
SUBSTRING(qt.TEXT, (qs.statement_start_offset/2)+1, 
((CASE qs.statement_end_offset 
WHEN -1 THEN DATALENGTH(qt.TEXT) 
ELSE qs.statement_end_offset 
END - qs.statement_start_offset)/2)+1), 
qs.execution_count, 
qs.total_logical_reads, 
qs.last_logical_reads, 
qs.total_logical_writes, qs.last_logical_writes, 
qs.total_worker_time, 
qs.last_worker_time, 
qs.total_elapsed_time/1000000 total_elapsed_time_in_S, 
qs.last_elapsed_time/1000000 last_elapsed_time_in_S, 
qs.last_execution_time,qp.query_plan 
FROM sys.dm_exec_query_stats qs 
CROSS APPLY sys.dm_exec_sql_text(qs.sql_handle) qt 
CROSS APPLY sys.dm_exec_query_plan(qs.plan_handle) qp 
ORDER BY qs.total_logical_reads DESC