Elencare le query in esecuzione su SQL Server


200

Esiste un modo per elencare le query attualmente in esecuzione su MS SQL Server (tramite Enterprise Manager o SQL) e / o chi è connesso?

Penso di avere una query molto lunga in esecuzione su uno dei miei server di database e mi piacerebbe rintracciarlo e fermarlo (o la persona che continua ad avviarlo).

Risposte:


203

Questo ti mostrerà gli SPID più lunghi in esecuzione su un server SQL 2000 o SQL 2005:

select
    P.spid
,   right(convert(varchar, 
            dateadd(ms, datediff(ms, P.last_batch, getdate()), '1900-01-01'), 
            121), 12) as 'batch_duration'
,   P.program_name
,   P.hostname
,   P.loginame
from master.dbo.sysprocesses P
where P.spid > 50
and      P.status not in ('background', 'sleeping')
and      P.cmd not in ('AWAITING COMMAND'
                    ,'MIRROR HANDLER'
                    ,'LAZY WRITER'
                    ,'CHECKPOINT SLEEP'
                    ,'RA MANAGER')
order by batch_duration desc

Se hai bisogno di vedere l'SQL in esecuzione per un dato spid dai risultati, usa qualcosa del genere:

declare
    @spid int
,   @stmt_start int
,   @stmt_end int
,   @sql_handle binary(20)

set @spid = XXX -- Fill this in

select  top 1
    @sql_handle = sql_handle
,   @stmt_start = case stmt_start when 0 then 0 else stmt_start / 2 end
,   @stmt_end = case stmt_end when -1 then -1 else stmt_end / 2 end
from    sys.sysprocesses
where   spid = @spid
order by ecid

SELECT
    SUBSTRING(  text,
            COALESCE(NULLIF(@stmt_start, 0), 1),
            CASE @stmt_end
                WHEN -1
                    THEN DATALENGTH(text)
                ELSE
                    (@stmt_end - @stmt_start)
                END
        )
FROM ::fn_get_sql(@sql_handle)

3
È possibile modificarlo per funzionare con SQL v12 + (ad es. Azure) rimuovendo i riferimenti al master, ad es. sostituire "master.dbo.sysprocesses" con "dbo.sysprocesses"
— Kevin,

Suggerirei di sostituire la msquantizzazione con s. Può verificarsi un possibile trabocco (è successo per me).
— Zverev Evgeniy,

Per Azure potresti dover cambiare "master.dbo.sysprocesses" con "sys.sysprocesses"
— Danton Heuer,

93

Se si esegue SQL Server 2005 o 2008, è possibile utilizzare i DMV per trovare questo ...

SELECT  *
FROM    sys.dm_exec_requests  
        CROSS APPLY sys.dm_exec_sql_text(sql_handle)  

1
Questa query non funziona in SQL Server 2005 se il livello di compatibilità del database corrente è inferiore a 90. Se la compatibilità del database corrente è inferiore, passare al db master per eseguire questa query.
— Alexander Pravdin,

31

È possibile eseguire il comando sp_who per ottenere un elenco di tutti gli utenti, le sessioni e i processi correnti. È quindi possibile eseguire il comando KILL su qualsiasi spid che sta bloccando gli altri.


3
Questo non è sempre utile. A volte le query sembrano generare spid figlio, specialmente quando vengono utilizzati OPENQUERY o server collegati. Può essere difficile dire quale sia la query principale solo da sp_who.
— Nathan,

17

Suggerirei di interrogare le sysviste. qualcosa di simile a

SELECT * 
FROM 
   sys.dm_exec_sessions s
   LEFT  JOIN sys.dm_exec_connections c
        ON  s.session_id = c.session_id
   LEFT JOIN sys.dm_db_task_space_usage tsu
        ON  tsu.session_id = s.session_id
   LEFT JOIN sys.dm_os_tasks t
        ON  t.session_id = tsu.session_id
        AND t.request_id = tsu.request_id
   LEFT JOIN sys.dm_exec_requests r
        ON  r.session_id = tsu.session_id
        AND r.request_id = tsu.request_id
   OUTER APPLY sys.dm_exec_sql_text(r.sql_handle) TSQL

In questo modo è possibile ottenere un TotalPagesAllocatedche può aiutarti a capire spidche sta prendendo tutte le risorse del server. Ci sono molte volte in cui non riesco nemmeno a visualizzare il monitor delle attività e utilizzare queste sysvisualizzazioni per vedere cosa sta succedendo.

Ti consiglierei di leggere il seguente articolo. Ho preso questo riferimento da qui .


1
Utilizziamo anche l'analisi delle prestazioni di Quest DB che fornisce un'ottima immagine visiva di ciò che accade nel server. Una delle cose brutte è che dice chi è la vittima, ma è difficile capire chi sta consumando le risorse. Ciò aiuterebbe però.
— dhi,


11

In realtà, l'esecuzione EXEC sp_who2in Query Analyzer / Management Studio fornisce più informazioni di sp_who.

Oltre a ciò, è possibile configurare SQL Profiler per monitorare tutto il traffico in entrata e in uscita verso il server. Profiler ti consente anche di restringere esattamente quello che stai cercando.

Per SQL Server 2008:

START - All Programs - Microsoft SQL Server 2008 - Performance Tools - SQL Server Profiler

Tieni presente che il profiler è davvero un'app di registrazione e visualizzazione. Continuerà a registrare e guardare fino a quando è in esecuzione. Potrebbe riempire file di testo o database o dischi rigidi, quindi fai attenzione a cosa hai guardato e per quanto tempo.


1
SQL Server Profiler è dove tutti dovrebbero iniziare, sicuramente!
— Shane,

11
SELECT
    p.spid, p.status, p.hostname, p.loginame, p.cpu, r.start_time, r.command,
    p.program_name, text 
FROM
    sys.dm_exec_requests AS r,
    master.dbo.sysprocesses AS p 
    CROSS APPLY sys.dm_exec_sql_text(p.sql_handle)
WHERE
    p.status NOT IN ('sleeping', 'background') 
AND r.session_id = p.spid

11

Come nota, è possibile trovare SQL Server Activity Monitor per SQL Server 2008 facendo clic con il tasto destro del mouse sul server corrente e andando su "Activity Monitor" nel menu contestuale. Ho scoperto che questo era il modo più semplice per terminare i processi se si utilizza SQL Server Management Studio.


Questo avrebbe dovuto essere un commento, ma, sì, è così utile e ottiene più visibilità come risposta :-) E mi ha aiutato in questo momento. Grazie
— Loudenvier,

9

In Esplora oggetti, eseguire il drill-down su: Server -> Gestione -> Monitoraggio attività. Ciò ti consentirà di vedere tutte le connessioni al server corrente.


1
Non vedo nulla chiamato Activity Monitor in Management su SQL 2008.
— jpierson

5

ecco una query che mostrerà tutte le query che stanno bloccando. Non sono del tutto sicuro che mostrerà solo query lente:

SELECT p.spid
,convert(char(12), d.name) db_name
, program_name
, convert(char(12), l.name) login_name
, convert(char(12), hostname) hostname
, cmd
, p.status
, p.blocked
, login_time
, last_batch
, p.spid
FROM      master..sysprocesses p
JOIN      master..sysdatabases d ON p.dbid =  d.dbid
JOIN      master..syslogins l ON p.sid = l.sid
WHERE     p.blocked = 0
AND       EXISTS (  SELECT 1
          FROM      master..sysprocesses p2
          WHERE     p2.blocked = p.spid )

5

La sceneggiatura giusta sarebbe così:

select 
p.spid, p.status,p.hostname,p.loginame,p.cpu,r.start_time, t.text
    from sys.dm_exec_requests as r, sys.sysprocesses p 
    cross apply sys.dm_exec_sql_text(p.sql_handle) t
    where p.status not in ('sleeping', 'background')
    and r.session_id=p.spid

5

È possibile utilizzare la query seguente per trovare l'ultima richiesta in esecuzione:

SELECT
    der.session_id
    ,est.TEXT AS QueryText
    ,der.status
    ,der.blocking_session_id
    ,der.cpu_time
    ,der.total_elapsed_time
FROM sys.dm_exec_requests AS der
CROSS APPLY sys.dm_exec_sql_text(sql_handle) AS est

Utilizzando lo script di seguito è inoltre possibile trovare il numero di connessione per database:

SELECT 
    DB_NAME(DBID) AS DataBaseName
    ,COUNT(DBID) AS NumberOfConnections
    ,LogiName 
FROM sys.sysprocesses
WHERE DBID > 0
GROUP BY DBID, LogiName

Per maggiori dettagli, visitare: http://www.dbrnd.com/2015/06/script-to-find-running-process-session-logged-user-in-sql-server/


4

nel 2005 è possibile fare clic con il pulsante destro del mouse su un database, andare ai report e c'è un intero elenco di report su transizioni e blocchi, ecc ...


4

Prova con questo:

Ti fornirà tutte le domande degli utenti. Fino a 50, sono solo sessioni di processo interne al server sql. Ma, se lo desideri, puoi rimuovere la clausola where:

select
r.session_id,
r.start_time,
s.login_name,
c.client_net_address,
s.host_name,
s.program_name,
st.text
from sys.dm_exec_requests r
inner join sys.dm_exec_sessions s
on r.session_id = s.session_id
left join sys.dm_exec_connections c
on r.session_id = c.session_id
outer apply sys.dm_exec_sql_text(r.sql_handle) st where r.session_id  > 50

3
SELECT 
    p.spid, p.status, p.hostname, p.loginame, p.cpu, r.start_time, t.text
FROM
    sys.dm_exec_requests as r,
    master.dbo.sysprocesses as p
    CROSS APPLY sys.dm_exec_sql_text(p.sql_handle) t
WHERE
    p.status NOT IN ('sleeping', 'background')
AND r.session_id = p.spid

E

KILL @spid

2
andrà bene .. !! e se uccido per spid. ucciderà solo una query? il mio dubbio è spid e session_is sono univoci per ogni query in esecuzione in quella sessione o server?
— buttowski,

1

Utilizzare Sql Server Profiler (menu Strumenti) per monitorare l'esecuzione di query e utilizzare Activity Monitor in Management Studio per vedere come è connessa e se la loro connessione sta bloccando altre connessioni.


Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.