اگر SQL Server بهطور کلی کند شده و مشکل به یک یا چند Query خاص برمیگردد، باید بدانی دقیقاً کدام کوئریها مقصر هستند. SQL Server چند ابزار قدرتمند برای این کار دارد — از نگاه سریع و لحظهای تا آمار تاریخی دقیق.
اگر همین الان سیستم کند است و میخواهی ببینی چه چیزی در حال اجراست، این کوئری کمک میکند:
SELECT r.session_id, r.status, r.command, r.cpu_time, r.total_elapsed_time, r.wait_type, SUBSTRING(t.text, (r.statement_start_offset/2)+1, ((CASE r.statement_end_offset WHEN -1 THEN DATALENGTH(t.text) ELSE r.statement_end_offset END - r.statement_start_offset)/2)+1) AS running_query FROM sys.dm_exec_requests r CROSS APPLY sys.dm_exec_sql_text(r.sql_handle) t WHERE r.session_id <> @@SPID ORDER BY r.total_elapsed_time DESC;
در SSMS میتوانی این را با Activity Monitor → Active Expensive Queries هم بهصورت گرافیکی ببینی.
برای دیدن آماری از Query هایی که در طول زمان بیشترین منابع را مصرف کردهاند (نه فقط همین لحظه)، از sys.dm_exec_query_stats استفاده کن:
SELECT TOP 20 qs.execution_count, qs.total_elapsed_time / qs.execution_count AS avg_elapsed_time_micro, qs.total_logical_reads / qs.execution_count AS avg_logical_reads, 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) AS query_text FROM sys.dm_exec_query_stats qs CROSS APPLY sys.dm_exec_sql_text(qs.sql_handle) qt ORDER BY avg_elapsed_time_micro DESC;
از SQL Server 2016 به بعد، Query Store بهترین ابزار برای این کار است چون تاریخچهی کامل عملکرد هر Query را حتی بعد از ریاستارت سرور نگه میدارد. ابتدا آن را فعال کن:
ALTER DATABASE ShopDB SET QUERY_STORE = ON;
بعد از فعالسازی، در SSMS مسیر Object Explorer → ShopDB → Query Store → Top Resource Consuming Queries یک نمودار گرافیکی از کندترین Query ها نشان میدهد — بدون نیاز به نوشتن کوئری.
وقتی Query مشکلدار را پیدا کردی، برای فهمیدن چرا کند است، Execution Plan آن را بررسی کن (در SSMS دکمهی Include Actual Execution Plan یا Ctrl+M). دنبال این نشانهها بگرد:
برای یادگیری کامل خواندن Execution Plan، درس Execution Plans را ببین.
| مشکل | راهحل |
|---|---|
| Table Scan روی جدول بزرگ | ساخت Nonclustered Index مناسب |
| آمار قدیمی | UPDATE STATISTICS یا فعالکردن Auto Update Statistics |
| SELECT * روی جدولهای عریض | فقط ستونهای لازم را انتخاب کن |
| JOIN بدون ایندکس روی کلید | ایندکس روی ستونهای JOIN بساز |
sys.dm_exec_requests یا Activity Monitor استفاده کن.sys.dm_exec_query_stats یا Query Store گزینهی بهتری است.فصل ایندکسگذاری و بهینهسازی دورهی SQLFarsi را ببین.
ادامهی یادگیری