¿Cómo puedo saber si todavía se está utilizando una base de datos de SQL Server?

33

Estamos buscando desmantelar una instancia de SQL Server que todavía tiene un par de bases de datos.

¿Cómo puedo saber si los usuarios o una aplicación web los siguen utilizando?

Encontré un hilo del foro que tenía una consulta T-SQL que podría ejecutar para recuperar la última fecha de consulta. Parece funcionar, pero quiero saber si esta información es lo suficientemente válida como para descartar bases de datos. ¿Lo es?

Si tiene métodos alternativos, eso también ayudaría.

jsauni
fuente
1
Mucha discusión a continuación, pero también vea esta publicación de blog .
Aaron Bertrand

Respuestas:

29

Tendría que preocuparse por los elementos que se han purgado de la memoria caché y que se ha perdido, o por las bases de datos que tienen un uso poco frecuente.

En lugar de descartar las bases de datos, colóquelas fuera de línea para evitar el acceso sin soltarlas o en el modo RESTRICTED_USER para limitar el acceso. Al hacer esto, puede dejarlos en ese estado durante un mes o dos para verificar si hay un uso ocasional.

También puede utilizar un filtro de rastreo del generador de perfiles del lado del servidor en esa base de datos.

NicCain
fuente
24
Regla n. ° 1 de ser un DBA: nunca haga ningún cambio del que no pueda retirarse rápidamente si es necesario.
Cayo
14

Estos son los métodos que he usado en el pasado:

  1. Poner la base de datos fuera de línea / Separar
  2. DENEGAR acceso de usuario / inicio de sesión
  3. Trazado de perfilador

El problema es este: ¿cuánto tiempo espera antes de estar seguro de que nadie va a acceder a los datos? Para los datos financieros, tiene algunos elementos que se ejecutan diariamente, semanalmente, mensualmente, trimestralmente, semestralmente y anualmente. ¿Pero es un año lo suficientemente largo? También he visto solicitudes para mantener los datos disponibles durante al menos 7 años, y en un caso me dijeron que los datos en un sistema tenían que estar allí para siempre, a pesar de que nadie los estaba usando.

El mejor consejo es este: hagas lo que hagas para desactivar el acceso, asegúrate de volver a activarlo de inmediato. Descubrí que la separación funcionó mejor para esto. Simplemente escribiría la reconexión e instruiría a mi equipo "si alguien pregunta dónde está, ejecute este script". Eso nos dio la mejor oportunidad de volver a poner las cosas lo más rápido posible.

SQLRockstar
fuente
He pensado en eso, si la cantidad de tiempo que superviso el uso de la base de datos fue suficiente. ¿Simplemente toma la naturaleza de SQL Server y hace esa llamada de juicio?
jsauni
Sí, en algún momento logrará que todos acepten desconectar, y que comprendan que si falla algún proceso no autorizado, tendrá que volver a poner las cosas rápidamente. siempre y cuando estén de acuerdo con una interrupción y vuelvas a poner las cosas en línea rápidamente, deberías estar bien. ¡pero no es fácil lograr que todos estén de acuerdo!
SQLRockstar
13

Estoy de acuerdo con Nic con su consejo. Si necesita estar seguro, entonces tendría que ir con Profiler (seguimiento del lado del servicio) porque algunas de las consultas SQL no se almacenarán en caché o, por cualquier motivo, el caché del procedimiento podría purgarse.

Normalmente verificaría la información de las estadísticas del archivo virtual también para ver si hay lecturas o escrituras en el nivel del archivo del sistema operativo. Incluso si la base de datos NO está activa, aún verá pequeñas lecturas / escrituras si está realizando copias de seguridad de registros, copias de seguridad completas, etc., pero eso también le dará una idea de la actividad de lectura / escritura en esa base de datos.

Antes de descartar cualquier base de datos, me aseguraría de que tenga al menos 2 o 3 copias de seguridad legibles (pruébelas) en ubicaciones separadas. Nunca se sabe cuando los necesita.

Sankar Reddy
fuente
8

La siguiente consulta muestra las bases de datos que no han tenido uso desde el último reinicio, sin depender de los planes de consulta que se mantienen en la memoria caché, ya que muestra las E / S del usuario en los índices (y montones). Esto es algo así como el uso de estadísticas de archivos virtuales, pero el DMV utilizado aquí excluye la actividad de E / S de las copias de seguridad. No es necesario mantener un seguimiento del generador de perfiles en ejecución, no se requieren disparadores ni auditorías. Por supuesto, si reinicia su servidor SQL con frecuencia (o adjunta / cierra bases de datos a menudo), este podría no ser el camino a seguir :-)

Habiendo dicho eso, todavía está de acuerdo en que, incluso si esta consulta parece confirmar que se puede descartar un DB, definitivamente desconecte / desconecte o niegue el acceso del usuario por algún tiempo, ¡además de cualquier diligencia debida de preguntar antes de caer realmente!

select [name] from sys.databases 
where database_id > 4
AND [name] NOT IN 
(select DB_NAME(database_id) 
from sys.dm_db_index_usage_stats
where coalesce(last_user_seek, last_user_scan, last_user_lookup,'1/1/1970') > 
(select login_time from sys.sysprocesses where spid = 1))
División de piso
fuente
Esto es bastante bueno si funciona bien. ¿Puedo preguntarte por qué estás tomando la fusión y comparándolo con login_time? ¿Y por qué no has incluido last_user_update? ¿Es este un intento inteligente de ver si una base de datos está recibiendo INSERTOS pero nadie la consulta? ¿O es posible que este DMV incluya todas las marcas de tiempo NULL?
Jason
2

Trabajé en un lugar que tenía una gran cantidad de bases de datos huérfanas y semi-huérfanas. Era difícil saber si realmente estaban huérfanos, ya que muchas tareas eran estacionales o anuales, por lo que el sitio web solo se ejecuta durante 3-4 meses por año (como ejemplo, los formularios W2 deben presentarse electrónicamente 1/31, por lo que el procesamiento del sitio web estos solo corrieron desde mediados de enero hasta finales de abril).

Lo que se hizo fue una combinación de:
* pregunte a cada desarrollador si estaban usando alguna base de datos u otra (estos correos electrónicos saldrían mensualmente o cada vez que las copias de seguridad tomaran demasiado tiempo).
* desconecte la base de datos y vea quién se queja.
* cambie el nombre del servidor para ver quién se queja.

Dado que el jefe de cabello puntiagudo solo estaba dispuesto a permitir la documentación "completa y completa", se prohibió expresamente un wiki y las reducciones de personal llevaron a una disminución dramática en la documentación que cumplió con el estándar.

Si fuera por mí, habría una página wiki por servidor con nombres de contacto para cada base de datos (y tal vez una breve descripción de para qué sirve la base de datos). Cualquier base de datos no documentada en la wiki sería un juego justo para su eliminación.

Teníamos un gran cliente financiero que todavía usaba SQL Server 2000 en 2009, por lo que tuvimos que mantener una instancia de SQL Server 2000 ejecutándose hasta que ese cliente finalmente se mudó a SQL Server 2005.

Tangurena
fuente
2

Otras dos alternativas son:

  1. Cree desencadenantes en la base de datos que le notificarán (o almacenarán en tablas) de cualquier actividad.
  2. Habilite la auditoría en las bases de datos.

    • Depende de su versión de base de datos.
StanleyJohns
fuente
2

La siguiente solución muestra páginas temporales totales, limpias y sucias en MB para bases de datos particulares bajo su instancia (encontradas en Internet y modificadas un poco):

SELECT
    (CASE WHEN ([database_id] = 32767) THEN 'Resource Database' ELSE DB_NAME (database_id) END) AS 'Database Name',
    COUNT(*) *8/1024 AS [TotalPages in MB],
    SUM(CASE WHEN ([is_modified] = 1) THEN 0 ELSE 1 END) *8/1024 AS [CleanPages in MB],
    SUM(CASE WHEN ([is_modified] = 1) THEN 1 ELSE 0 END) *8/1024 AS [DirtyPages in MB]
FROM sys.dm_os_buffer_descriptors
GROUP BY database_id
ORDER BY DB_NAME(database_id)

o

select value [DBid],attribute, last_execution_time ,text
from
sys.dm_exec_query_stats
cross apply
sys.dm_exec_plan_attributes(plan_handle)
cross apply
sys.dm_exec_sql_text(plan_handle)
where  attribute = 'dbid' 
order by last_execution_time desc

o

select value [DBid],attribute, last_execution_time ,text
from
sys.dm_exec_query_stats
cross apply
sys.dm_exec_plan_attributes(plan_handle)
cross apply
sys.dm_exec_sql_text(plan_handle)
--where dbid=8
where 
      text like '%idAdministrator%' and
      attribute = 'dbid' 
      and value>= 5 -- dbid >=5 for user databases but include resource database which
                     --you can exclude by its numer I don't remember at the moment
order by last_execution_time desc
SQL Server Frant
fuente
2
¿Podría aclarar cómo resuelve esto el problema original?
dezso