Sp who: примеры (SQL)

Использование функции sp_who для анализа активности в SQL Server
Раздел: Системные административные функции, Мониторинг
sp_who([@loginame =] 'login'): N/A

Функция sp_who в MS SQL Server

Функция sp_who является системной хранимой процедурой в Microsoft SQL Server, предназначенной для отображения информации о текущих пользователях, сессиях и процессах в экземпляре СУБД. Её основное применение — мониторинг активности и диагностика проблем, связанных с блокировками, долгими запросами или перегрузкой сервера.

Процедура возвращает табличный результат (результирующий набор) со следующими столбцами:

  • spid (smallint) — идентификатор процесса сервера (сессии).
  • ecid (smallint) — идентификатор контекста выполнения для конкретного процесса (поток внутри сессии).
  • status (nchar(30)) — статус процесса (например, running, sleeping, background).
  • loginame (nchar(128)) — имя входа, связанное с процессом.
  • hostname (nchar(128)) — имя компьютера, с которого установлено соединение.
  • blk (char(5)) — идентификатор процесса, который блокирует текущий (если есть блокировка).
  • dbname (nchar(128)) — имя базы данных, используемой процессом.
  • cmd (nchar(16)) — тип команды, выполняемой процессом (например, SELECT, UPDATE, AWAITING COMMAND).
  • request_id (int) — идентификатор запроса в рамках сессии.

Процедура поддерживает один необязательный параметр:

  • @loginame (sysname) — фильтр по имени входа. Если параметр указан, возвращаются процессы для конкретного пользователя. При значении 'active' исключаются процессы с состоянием 'sleeping'.

Примеры вызова sp_who

Базовый вызов для получения информации обо всех процессах.

EXEC sp_who;
spid | ecid | status    | loginame | hostname | blk  | dbname  | cmd
51 | 0 | sleeping | sa | SRV01 | NULL | master | AWAITING COMMAND
52 | 0 | running | user1 | WS01 | NULL | MyDB | SELECT

Использование параметра для фильтрации по имени входа.

EXEC sp_who @loginame = 'user1';
spid | ecid | status  | loginame | hostname | blk  | dbname | cmd
52 | 0 | running | user1 | WS01 | NULL | MyDB | SELECT

Использование флага 'active' для исключения спящих процессов.

EXEC sp_who 'active';
spid | ecid | status  | loginame | hostname | blk  | dbname  | cmd
52 | 0 | running | user1 | WS01 | NULL | MyDB | SELECT
53 | 0 | running | user2 | WS02 | 52 | MyDB | UPDATE

Похожие функции в MS SQL Server

В современных версиях SQL Server предпочтительнее использовать динамические административные представления (DMV).

  • sys.dm_exec_sessions — предоставляет расширенную информацию о всех активных сессиях. Содержит больше столбцов, чем sp_who, включая время начала, используемую память и др. Используется для детального анализа сессий.
  • sys.dm_exec_requests — возвращает данные о выполняющихся в данный момент запросах. Позволяет увидеть текст запроса, план выполнения, статистику ввода-вывода. Применяется для поиска долгих или проблемных запросов.
  • sys.sysprocesses — системное представление, лежащее в основе sp_who. Рекомендуется использовать DMV, так как sys.sysprocesses считается устаревшим.

Выбор зависит от задачи: sp_who подходит для быстрой проверки, DMV — для глубокой диагностики.

Аналоги функции в других СУБД

В других базах данных существуют схожие механизмы для мониторинга сессий.

MySQL: Команда SHOW PROCESSLIST или запрос к INFORMATION_SCHEMA.PROCESSLIST.

SHOW FULL PROCESSLIST;
Id | User | Host          | db   | Command | Time | State | Info
5 | root | localhost:1234 | test | Query | 0 | init | SELECT * FROM users

PostgreSQL: Представление pg_stat_activity.

SELECT pid, usename, client_addr, state, query FROM pg_stat_activity;
pid  | usename | client_addr | state  | query
1234 | postgres| 192.168.1.1 | active | SELECT * FROM orders;

Oracle: Запрос к представлениям V$SESSION или V$PROCESS.

SELECT sid, serial#, username, machine, program FROM v$session;
SID | SERIAL# | USERNAME | MACHINE  | PROGRAM
123 | 456 | APP_USER | SRV_DB | sqlplus.exe

SQLite: Прямых аналогов нет из-за файловой архитектуры. Мониторинг осуществляется через средства операционной системы.

Отличие от MS SQL: в PostgreSQL и Oracle представления предоставляют более детальную информацию о состоянии запросов и ресурсах.

Типичные ошибки при использовании

Основные ошибки связаны с неверной интерпретацией данных или устаревшим синтаксисом.

1. Попытка фильтрации по несуществующему логину — процедура вернет пустой набор, но ошибки не произойдет.

EXEC sp_who @loginame = 'nonexistent_user';
(нет строк)

2. Использование устаревшего синтаксиса без ключевого слова параметра. Раньше допустимо было указывать значение без имени параметра, но такой стиль не рекомендуется.

EXEC sp_who 'sa'; -- Работает, но менее читаемо

3. Ожидание, что процедура покажет детальную информацию о блокировках. Для этого лучше использовать sys.dm_tran_locks или sp_lock.

4. Непонимание столбца blk: значение NULL не означает отсутствие блокировок вообще, а указывает, что данный процесс не ожидает снятия блокировки другим процессом.

Изменения в последних версиях

Сама процедура sp who остаётся неизменной для обеспечения обратной совместимости. Однако, начиная с SQL Server 2005, корпорация Microsoft рекомендует использовать динамические административные представления (DMV), такие как sys.dm_exec_sessions и sys.dm_exec_requests, как более мощные и эффективные средства диагностики.

В SQL Server 2012 и позднее никаких существенных изменений в sp who не вносилось. Основные улучшения в области мониторинга касаются именно DMV и расширенных событий (Extended Events).

Расширенные примеры использования

Объединение результатов sp_who с другими системными представлениями для получения детальной информации.

Поиск процессов, блокирующих другие, с определением текста блокирующего запроса.

Пример sql
SELECT
t1.spid AS blocked_spid,
t1.blk AS blocking_spid,
t1.loginame AS blocked_login,
t2.loginame AS blocking_login,
t1.cmd AS blocked_command,
t2.cmd AS blocking_command,
er.query_plan AS blocking_query_plan
FROM sp_who t1
INNER JOIN sp_who t2 ON t1.blk = t2.spid
OUTER APPLY sys.dm_exec_sql_text(
(SELECT sql_handle FROM sys.sysprocesses WHERE spid = t2.spid)
) AS est
OUTER APPLY sys.dm_exec_query_plan(
(SELECT plan_handle FROM sys.sysprocesses WHERE spid = t2.spid)
) AS er
WHERE t1.blk > 0;
blocked_spid | blocking_spid | blocked_login | blocking_login | blocked_command | blocking_command
55 | 54 | user_app | user_batch | SELECT | UPDATE

Мониторинг активности в конкретной базе данных с фильтрацией по её имени.

Пример sql
DECLARE @dbname NVARCHAR(128) = 'MyDatabase';
EXEC sp_who;
-- Затем ручная фильтрация по столбцу dbname в результатах
-- Или использование sys.sysprocesses напрямую:
SELECT * FROM sys.sysprocesses WHERE dbid = DB_ID(@dbname);

Определение количества активных соединений для каждого логина.

Пример sql
SELECT 
loginame,
COUNT(*) AS session_count,
SUM(CASE WHEN status != 'sleeping' THEN 1 ELSE 0 END) AS active_sessions
FROM sp_who
GROUP BY loginame
ORDER BY session_count DESC;
loginame | session_count | active_sessions
sa | 5 | 2
user1 | 3 | 1

MS SQL sp_who function comments

En
Sp who Provides information about current users, sessions, and processes