Preguntas y respuestas de SQLTablas temporales, procesamiento de 64 bits, creación de reflejos y más

Editado por Nancy Michell

Tablas temporales

P Tengo entendido que, para evitar problemas de contención, no siempre es recomendable usar la base de datos temporal, tempdb. ¿Es cierto? La he usado porque necesito obtener datos distribuidos entre varias tablas e, incluso, ir modificándolos. Esto no resulta fácil con las vistas.

R Es cierto que un uso excesivo de tempdb puede dar lugar a situaciones de contención. Pero, por lo general, la contención sólo supone un problema en contadas ocasiones; por ejemplo, cuando se obtienen centenares de SPID (identificadores de proceso de servidor) que crean y eliminan muchas tablas temporales simultáneamente, tal como se explica en el artículo de Knowledge Base support.microsoft.com/kb/328551 (puede estar en inglés).

El uso de una tabla temporal (que, por cierto, puede encontrarse en tempdb o no) puede ofrecer una solución satisfactoria. La clave radica en si el aumento de rendimiento obtenido al extraer datos de la tabla temporal compensa la sobrecarga que supone generar primero la tabla.

Deberán considerarse el tamaño, la duración, la frecuencia de uso y, en particular, el número de instancias activas de la(s) tabla(s) temporal(es) antes de rechazar la solución. Las dimensiones de los servidores también son importantes, ya que la contención en torno a tempdb puede estar relacionada con el hardware.

Si necesita un gran número de tablas pequeñas y de corta duración, puede probar con variables de tabla, que presentan algunas ventajas con respecto a las tablas temporales. (Consulte la respuesta a nuestra siguiente pregunta para obtener más detalles acerca de las diferencias entre variables de tabla y tablas temporales, y lea "Preguntas más frecuentes: SQL Server 2000 - Variables de tablas" para obtener más información).

En su caso, si todas las consultas a la base de datos deben pasar por los procedimientos de creación de tablas temporales, quizá también resulte prudente cuestionar el modelo de datos original, en lugar de intentar aceptarlo sin más.

P ¿Qué son las variables de tabla y cómo es su rendimiento? ¿Es verdad que puedo usarlas en lugar de las tablas temporales?

R Las tablas temporales y las variables de tabla proporcionan la misma funcionalidad básica; ambas se materializan como tablas temporales en la base de datos tempdb. Sin embargo, cuando sólo se inserta un número reducido de filas, las variables de tabla pueden proporcionar un rendimiento superior. Esto es debido a que las variables de tabla no mantienen estadísticas o índices, lo que supone una menor sobrecarga. Si el contenido de la tabla no supera un número reducido de páginas de 8 KB almacenadas en la caché de datos por el motor de la base de datos, son preferibles las variables de tabla.

Por lo que respecta a los Libros en pantalla de SQL Server™:

  • Una variable de tabla se comporta como una variable local. Tiene un ámbito bien definido, que es la función, el procedimiento almacenado o el lote en el que se declara. Dentro de su ámbito, una variable de tabla se puede usar como una tabla normal.
  • Las variables de tabla se limpian automáticamente al final de la función, el procedimiento almacenado o el lote en el que se definen.
  • Las variables de tabla usadas en los procedimientos almacenados provocan menos compilaciones nuevas de los procedimientos almacenados que cuando se usan tablas temporales.
  • Las variables de tabla requieren menos recursos de bloqueo y registro.
  • En algunos casos puede mejorar el rendimiento, aunque no se guardan estadísticas.

Creación de reflejos

P He previsto usar la función de creación de reflejos de SQL Server 2005 para ofrecer un alto nivel de disponibilidad. El sistema se ejecutará en modo de alta disponibilidad para posibilitar la conmutación por error automática. Pero también deseo ejecutar otras aplicaciones en el reflejo para utilizar plenamente el recurso. El servidor reflejado admitirá dos bases de datos: La base de datos de producción, como reflejo de la principal, y la base de datos de ensayo, como independiente. También admitirá dos tipos de clientes: uno se configura con conmutación por error en la creación de reflejos para el acceso a la base de datos de producción, mientras que el otro se conecta directamente a la base de datos de ensayo.

Además, algunos paquetes de SQL Server Integration Services (SSIS) se ejecutarán en el servidor reflejado. Tendrán acceso a ambas bases de datos, al transferir los datos desde la de ensayo local a la de producción que se ejecuta en el servidor principal. Durante la conmutación por error, los paquetes de SSIS transferirán los datos desde la base de datos de ensayo local a la base de datos de producción local (conmutación por error). ¿Existe algún problema relacionado con estas configuraciones que deba tener presente?

R En general, esta clase de configuración no se recomienda porque, tras una conmutación por error, la distribución podría quedar descompensada hacia el nuevo principal.

Desde el punto de vista funcional, no parece que deba de haber problemas por lo que respecta a la creación de reflejos, pero debe comprobarse exhaustivamente si se va a adoptar esta solución. Las pruebas deben realizarse con picos de carga, en configuración estándar y tras la conmutación por error. Y los picos de carga deben corresponder a cálculos sobre valores futuros, no a cargas máximas actuales; si no se tienen en cuenta las necesidades empresariales futuras, la solución dejará de ser operativa cuando la carga sobrepase el límite de la capacidad.

Las pruebas podrían revelar cuellos de botella de red, de discos e, incluso, de CPU, que se manifestarían en forma de tiempos de respuesta de aplicación excesivos, un rendimiento inaceptable, errores de tiempo de espera o colas excesivas para la puesta al día (lo que podría provocar tiempos de conmutación por error inesperadamente prolongados, en función de la tasa real de operaciones de puesta al día).

Además, durante la conmutación por error, los paquetes que se ejecuten perderán la conexión con el principal defectuoso. Cuando se complete la conmutación por error y la base de datos esté disponible en el nuevo principal, los paquetes deben poder volver a conectarse al nuevo principal. Naturalmente, se supone que los paquetes se han construido con mecanismos de reintento de conectividad y que controlarán correctamente los errores de conexión, de modo que sea posible la recuperación a partir de condiciones de conexión interrumpida, por ejemplo.

SQL Server y sistemas operativos de 64 bits

P ¿Es verdad que, si en mi equipo se ejecuta una versión de 64 bits de un sistema operativo Windows Server®, debo usar SQL Server 2000 Enterprise Edition (64 bits) y no puedo usar SQL Server 2000 de 32 bits?

R Por lo que respecta a SQL Server 2000, la única arquitectura nativa de 64 bits compatible es ia64 de Intel. Así pues, cuando en el contexto de SQL Server 2000 se hace referencia a compatibilidad con 64 bits, se trata de ia64. La única versión de SQL Server 2000 que se admite en ia64 de 64 bits de forma nativa es Enterprise Edition. No hay ninguna versión Standard Edition de SQL Server 2000 que se ejecute en ia64; ni de forma nativa como aplicación de 64 bits, ni en ia64 Windows® en Windows (WOW, un subsistema de SO que permite ejecutar aplicaciones de 32 bits).

En el caso de un equipo AMD x64, dispone de dos opciones con SQL Server 2000. Puede ejecutar un sistema operativo de 32 bits, en cuyo caso se ejecutará cualquier edición de SQL Server 2000 y Service Pack (SP). O bien, ejecutar un sistema operativo de 64 bits y SQL Server 2000 (cualquier edición) SP4 en WOW. En ese entorno, SQL Server 2000 no es una aplicación de 64 bits nativa. Se ejecuta en WOW en modo de 32 bits, totalmente al margen del mundo de los 64 bits.

Para complicar un poco más las cosas, WOW ia64 y WOW x64 son dos subsistemas totalmente distintos. En ia64, WOW debe emular un espacio de direcciones virtuales restringido y, al mismo tiempo, llevar a cabo la emulación real de instrucciones de código máquina. Las instrucciones de código máquina son totalmente distintas de las de x86: se trata de un diseño completamente diferente. SQL Server no admite ninguno de sus componentes (SQL Server 2000 o SQL Server 2005) cuando se ejecuta en WOW ia64.

Sin embargo, el panorama es diferente con WOW x64. Las arquitecturas x86 y x64 son muy parecidas. El conjunto de instrucciones es el mismo (o casi el mismo), por lo que sólo se debe emular el espacio de direcciones virtuales de 32 bits (y para ello existe ayuda a través del hardware). Por lo tanto, hay muchos componentes de SQL Server compatibles con WOW x64, como SQL Server 2000 SP4 y todas las ediciones de SQL Server 2005.

Actualización a SQL Server 2005

P Deseo realizar la actualización de SQL Server 2000 a SQL Server 2005. Además de la corrección de código SQL, ¿qué cambios hay que hacer en las aplicaciones? Por ejemplo, si conecto SQL Server 2005 con un cliente de Microsoft® .NET Framework, ¿debo actualizar mis clientes de escritorio a Windows XP SP2?

Trabajo con Windows XP SP1 y Visual Basic® 6.0, así como con algunas aplicaciones que usan .NET. ¿Se necesitan SQL Server Native Client, .NET Framework 2.0 y Windows XP SP2? Es decir, ¿cuáles son los requisitos mínimos generales de cliente para una actualización? Y si decido adoptar la funcionalidad de creación de reflejos de SQL Server 2005, ¿cambian los requisitos por lo que respecta a los clientes?

R Para aprovechar plenamente la característica de creación de reflejos, debe usar SQL Native Client (para OleDb u ODBC) o ADO.NET 2.0 SqlClient. Y la cadena de conexión debe cambiar para hacer referencia tanto al principal como al reflejo.

Pero sólo necesita SQL Native Client o .NET Framework 2.0 para que el cliente pueda trabajar con reflejos. Los clientes más antiguos pueden conectarse, pero no intentarán trabajar automáticamente con el reflejo si el principal no funciona.

Sin necesidad de tocar los clientes, puede agregar un conmutador BIG-IP entre los clientes y el servidor para moverlos manualmente en caso de conmutación por error. O bien, puede cambiar código de la aplicación para intentar una conexión al servidor reflejado cuando se produzca un error de conexión con el principal.

Entre los requisitos del sistema se encuentran los siguientes: Windows Installer 3.0, Microsoft Windows XP SP1 o posterior, Microsoft Windows 2000 SP4 o posterior, o Microsoft Windows Server 2003. Para obtener más información acerca de los requisitos, consulte "Uso de ADO con SQL Native Client"; "Actualización de una aplicación a SQL Native Client desde MDAC" y "Requisitos del sistema para SQL Native Client"

Memoria insuficiente de SQL Server 2000

P Aparecen extrañas excepciones de memoria insuficiente en mi versión de producción de SQL Server 2000 Enterprise Edition SP4 con Windows Server 2003 SP1. En la figura 1 se muestra el error extraído de los registros.

Figure 1 Error de memoria insuficiente

2006-06-23 14:41:40.72 spid77    WARNING:  Failed to reserve contiguous memory of Size= 24641536.
2006-06-23 14:41:40.85 spid77    Buffer Distribution:  Stolen=4800 Free=1744 Procedures=39391
                                Inram=0 Dirty=90621 Kept=0
                                I/O=0, Latched=99, Other=3063345
2006-06-23 14:41:40.85 spid77    Buffer Counts:  Commited=3200000 Target=3200000 Hashed=3154065
                                InternalReservation=587 ExternalReservation=0 Min Free=1024 Visible= 173320
2006-06-23 14:41:40.85 spid77    Procedure Cache:  TotalProcs=9555 TotalPages=39391 InUsePages=1031
2006-06-23 14:41:40.85 spid77    Dynamic Memory Manager:  Stolen=44191 OS Reserved=7648 
                                OS Committed=7619
                                OS In Use=7603
                                Query Plan=39088 Optimizer=0
                                General=4183
                                Utilities=140 Connection=7651
2006-06-23 14:41:40.85 spid77    Global Memory Objects:  Resource=1617 Locks=313 
                                SQLCache=1836 Replication=204
                                LockBytes=2 ServerGlobal=42
                                Xact=63
2006-06-23 14:41:40.85 spid77    Query Memory Manager:  Grants=0 Waiting=0 Maximum=94533 Available=94533
2006-06-23 14:41:40.88 spid77    Error: 17803, Severity: 20, State: 12
2006-06-23 14:41:40.88 spid77    Insufficient memory available..

Mi servidor tiene una gran cantidad de memoria RAM (32 GB). Curiosamente, este problema parece producirse de forma aleatoria; el procedimiento almacenado que provoca este error lo hace una o dos veces de cada 20 ejecuciones.

Los contadores de rendimiento del servidor indican que hay una gran cantidad de memoria disponible. ¿Es posible que el escritor diferido no pagine en el disco con la suficiente rapidez? ¿Por qué solicita el proceso tanta memoria cuando ejecuta mi procedimiento almacenado? ¿Se trata del número de instrucciones select o del uso de tablas temporales?

R La cantidad de memoria física del equipo no es relevante en este caso. En función de cómo se haya configurado boot.ini, las aplicaciones tendrán entre 2 y 3 GB de espacio de direcciones virtuales. El espacio de direcciones virtuales es un bien muy preciado en los sistemas de 32 bits. De forma predeterminada, el grupo de búferes dejará de consumir 384 MB del espacio de direcciones virtuales. Esos 384 MB se reservan para pilas de subprocesos y asignaciones de componentes que son demasiado grandes para ser atendidos por el grupo de búferes, o que no se han preparado para realizar asignaciones desde el grupo de búferes (procedimientos extendidos de terceros, servidores vinculados o componentes COM).

La advertencia indica que se produjo un error en una asignación de unos 23 MB. El hecho de que prosperen o no las asignaciones de este tamaño dependerá del número y la colocación de otras asignaciones en el bloque de 384 MB.

Podría plantearse la posibilidad de quitar algunos de los procedimientos extendidos de terceros que están cargados en el sistema, determinando si se usan componentes COM a través de sp_oacreate o servidores vinculados.

Es muy posible que el proceso solicite una cantidad de memoria tan considerable cuando ejecute su procedimiento almacenado de SQL debido al uso de la cláusula FOR XML en su procedimiento almacenado (que no reproducimos aquí). Sin embargo, si desea más información, Process\sqlservr\Virtual Bytes le proporcionará una indicación de cuánto espacio de direcciones virtuales sigue aún disponible. Y hay una herramienta denominada VMStat (que se incluye en el CD del libro Programming Applications for Microsoft Windows, de Jeffrey Richter) que determinará el tamaño del bloque de direcciones virtuales mayor. El escritor diferido no participa en esta asignación; el área de memoria que se usa para la asignación no está en bpool.

Mis agradecimientos a los siguientes profesionales de TI de Microsoft por la aportación de sus conocimientos técnicos: Ramon Arjona, Stephen Borg, Sandu Chirica, Robert Djabarov, Guillaume Fourrat, Osamu Hirayama, Alejandro Mihanovich, Maxwell Myrick, Uttam Parui, Shashi Ramaka, Gavin Sharpe, Vijay Sirohi, Jimmie Thompson, Madhusudhanan Vadlamaani, Jian Wang y Dave Wickert.

© 2008 Microsoft Corporation and CMP Media, LLC. Reservados todos los derechos; queda prohibida la reproducción parcial o total sin previa autorización.