Los tiempos de las consultas a cabo cuando se ejecuta desde la web, pero super-rápido cuando se ejecuta desde SSMS

StackOverflow https://stackoverflow.com/questions/2248112

Pregunta

Estoy tratando de depurar el código fuente de un tiempo de espera de SQL en una aplicación web que mantengo.Tengo el código fuente de C# código de atrás, así que sé exactamente de qué código se está ejecutando.He depurado la aplicación a la derecha hacia abajo a la línea que se ejecuta el código SQL que se agota, y veo que la consulta que se ejecuta en el analizador de SQL.

Cuando esta consulta se ejecuta desde la web, se desconecta después de 30 segundos.Sin embargo, cuando yo cortar/pegar la consulta tal y como se presenta en el Analizador, y lo puse en SSMS y ejecutarlo, devuelve casi al instante.He rastreado el problema a ARITHABORT está ajustado a OFF en la conexión que la web que está utilizando (es decir, si me dirijo a ARITHABORT OFF en el SSMS período de sesiones, ejecuta durante un largo tiempo, y si me dirijo DE nuevo a continuación, se ejecuta muy rápidamente).Sin embargo, la lectura de la descripción de ARITHABORT, no parece aplicar...Sólo estoy haciendo un SELECT simple, y NO hay aritmética que se realiza en todos..solo un INNER JOIN con una condición where:

¿Por qué ARITHABORT OFF ser la causa de este comportamiento en este contexto??Hay alguna manera de que pueda alterar la configuración de ARITHABORT para que la conexión desde SSMS?Estoy usando SQL Server 2008.

¿Fue útil?

Solución

Así que su código C # es el envío de una consulta SQL hoc aviso de SQL Server, mediante qué método? Ha considerado el uso de un procedimiento almacenado? Eso probablemente garantizar el mismo rendimiento (al menos en el motor), independientemente de quién lo llamó.

¿Por qué? El ajuste ARITHABORT es una de las cosas que el optimizador de mira a la hora que es la determinación de la forma de ejecutar la consulta (más específicamente, para la adaptación del plan). Es posible que el plan en caché tiene la misma configuración que SSMS, por lo que utiliza el plan almacenado en caché, pero con el contrario el establecimiento de su código C # está obligando a una recompilación (o tal vez usted está golpeando realmente un BAD Plan en la memoria caché), que sin duda puede perjudicar el rendimiento en muchos casos.

Si ya está llamando a un procedimiento almacenado (que no se hayan publicado la consulta, aunque yo creo que hayas querido), puede intentar añadir OPCIÓN (RECOMPILE) a la consulta infractor (o consultas) en el procedimiento almacenado. Esto significará esos estados siempre recompilar, pero podría impedir el uso del mal plan que parece estar golpeando. Otra opción es asegurarse de que cuando se compila el procedimiento almacenado, el lote se ejecuta con SET EN ARITHABORT.

Por último, usted parece estar preguntando cómo se puede cambiar la configuración ARITHABORT en SSMS. Creo que lo que quería preguntar es cómo se puede forzar el ajuste ARITHABORT en el código. Si decide continuar enviando SQL ad hoc de su aplicación de C #, entonces, por supuesto, puede enviar un comando como texto que tiene varias sentencias separadas por punto y coma, por ejemplo:.

SET ARITHABORT ON; SELECT ...

Para obtener más información acerca de por qué se produce este problema, consulte el artículo de gran Erland Sommarskog:

Otros consejos

Esta respuesta incluye una forma de resolver este problema:

Ejecutando los siguientes comandos como administrador en la base de datos de todas las consultas que se ejecuta como se esperaba, independientemente de la configuración de ARITHABORT.

 DBCC DROPCLEANBUFFERS
 DBCC FREEPROCCACHE

Actualización

Parece que la mayoría de las personas terminan teniendo este problema se producen muy rara vez, y la técnica anterior es una decente a tiempo de corregir.Pero si una consulta específica que presenta este problema más de una vez, más a largo plazo, la solución a este problema sería utilizar las Sugerencias de Consulta como OPTIMIZE FOR y OPTION(Recompile), como se describe en este artículo.

He tenido este problema muchas veces antes, pero si usted tiene un procedimiento almacenado con el mismo problema dejando caer y volver a crear el procedimiento almacenado va a resolver el problema.

Se llama descubrimiento de parámetros. Es necesario localizar siempre los parámetros en el procedimiento almacenado para evitar este problema en el futuro.

Entiendo que esto podría no ser lo que quiere el cartel original, pero podría ayudar a alguien con el mismo problema.

Si se utiliza Entity Framework debe tener en cuenta que los parámetros de consulta para los valores de cadena se envían a la base de datos como nvarchar por defecto, si la columna de base de datos para comparar se escribe varchar, dependiendo de su cotejo, el plan de ejecución de la consulta puede requerir una "conversión implícita" paso, que obliga a un análisis completo. Podría confirmarlo mirando en el monitoreo de base de datos en la opción de consultas caro, lo que muestra el plan de ejecución.

Por último, una explicación de este comportamiento en este artículo: https://www.sqlskills.com/blogs / jonathan / implícitos-conversiones-que-causa-index-exploraciones /

Yo tenía el mismo problema y lo arreglaron mediante la ejecución de procedimiento "CON RECOMPILE". También puede tratar de usar la inhalación de parámetro. Mi problema se relaciona con la memoria caché de SQL.

Si usted puede cambiar su código para fijar descubrimiento de parámetros a optimizar para la pista desconocida es su mejor opción. Si no puede cambiar su código es la mejor opción exec sp_recompile 'nombre de proc' lo que obligará a que una única procedimiento almacenado para obtener un nuevo plan de ejecución. Dejar caer y volver a crear un proc tendría un efecto similar, pero podría causar errores si alguien intenta ejecutar el proc mientras tiene que caer. DBCC FREEPROCCACHE cae todos sus planes en caché que puede causar estragos bien su sistema hasta e incluyendo causando un montón de tiempo de espera en un entorno de producción transacciones pesada. Configuración arithabort no es una solución al problema, pero es una herramienta útil para descubrir si el parámetro olfateo es el problema.

Tengo el mismo problema al intentar llamar SP de SMSS tardó 2 seg, mientras que de la aplicación de web (ASP.NET) que tomó cerca de 3 min.

He intentado todas las soluciones sugeridas sp_recompile, DBCC FREEPROCCACHE y DBCC DROPCLEANBUFFERS pero nada fijo mi problema, pero cuando probé descubrimiento de parámetros que hizo el truco, y funcionaba bien.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top