DECLARE @sess varchar(7)I created a SQL Server Agent job that runs this every ten minutes. This sends me an eMail when something is spinning up a lot of read activity, but it also filters out queries to just those missing a Where clause or a Top restriction.
DECLARE @emMsg varchar(270)
DECLARE @sqlRun varchar(200)
set @sess = NULL
select TOP(1) @sess = ql.session_id, @sqlRun = ql.query_text from
(
select r.session_id
,substring(qt.text,r.statement_start_offset/2,
(case when r.statement_end_offset = -1
then len(convert(nvarchar(max), qt.text)) * 2
else r.statement_end_offset end - r.statement_start_offset)/2)
as query_text, r.cpu_time, r.total_elapsed_time
, r.reads, r.logical_reads
from sys.dm_exec_requests as r
cross apply sys.dm_exec_sql_text(sql_handle) as qt
inner join sys.dm_exec_sessions as es on r.session_id = es.session_id
where es.is_user_process = 1
) as ql
where ql.query_text not like '%where%'
and ql.query_text not like '%top%'
and ql.logical_reads > 200000
IF @sess is not null
BEGIN
set @emMsg = 'Session id ' + @sess + ' Running ' + @sqlRun
EXEC msdb.dbo.sp_send_dbmail
@profile_name='SqlEntNotifications',
@recipients = 'jdchapman@mycompany.com',
@subject = 'Unbounded Query Alert',
@body = @emMsg
END
It's not perfect enough that I might automatically kill SPIDs; sometimes it sends along an eMail from a long-running production job -- actually a good thing, as it alerts me to places I might have to trace or optimize later. It does tend to help me keep the SQL instance generally out of trouble though.
No comments:
Post a Comment