Sql Timeout dans l'application mais pas dans Sql Server Mgmt Studio

J'ai cette procédure stockée relativement complexe qui effectue une search dans la database. C'est un bon 400 lignes, mais quand je l'exécute dans Sql Server Management Studio en utilisant un paramètre de search qui ne renverra aucun hit, il faut environ 1 à 3 secondes pour terminer. Il faut presque le même time pour exécuter une search qui renvoie quelques centaines de lignes.

Toutefois, lorsque je l'exécute à partir d'une application Web qui appelle cette procédure stockée, en utilisant les mêmes parameters de search, elle ne renvoie jamais de résultat. J'ai augmenté les timeouts de connection et de command à 5 minutes, et ne revient jamais. En fait, cela prend les 5 minutes que je lui ai permises avant qu'il ne lève une exception de timeout.

Ce timeout d'attente se produit à la fois sur un server Web et sur mon post de travail, par rapport à une database de production.

Des idées sur ce que je pourrais être contre? Le code est C #, et j'ai exécuté le code Microsoft.Practices.EnterpriseLibrary ainsi que le code SqlClient directement, à l'intérieur d'une clause using et sans un. Il y a 19 parameters, et voici donc une version abrégée de ma dernière tentative:

IList<QueryResultsItem> resultsItem = new List<QueryResultsItem>(); ssortingng connSsortingng = "server=[servername];database=[dbname];uid=[userid];pwd=[psw];Connection Timeout=300"; SqlConnection conn = new SqlConnection(connSsortingng); conn.Open(); SqlCommand cmd = new SqlCommand(); cmd.CommandTimeout = 300; cmd.Connection = conn; cmd.CommandText = "ap_tems_get_batch_history_list"; cmd.CommandType = CommandType.StoredProcedure; SqlParameter parm = new SqlParameter(); parm.ParameterName = "@parm"; parm.Value = [value]; parm.Size = 3; parm.SqlDbType = SqlDbType.Char; cmd.Parameters.Add(parm); ... SqlDataReader reader = cmd.ExecuteReader(); 

J'ai rencontré pas mal de problèmes de ce genre dans les applications web. Voici mes conclusions.

  1. SSMS se connecte à la database et s'exécute directement via le fournisseur sql.
  2. Les applications Web traversent toute la stack Microsoft depuis IIS, les couches de gestion, …, puis le fournisseur sql vers la database. C'est une raison.
  3. C'est la raison principale. votre code C # construit les params, et parle à la database à travers un process de schéma de database / métadonnées / informations, ce qui prend beaucoup plus de time. Si vous définissez le sharepoint rupture du débogueur autour du SqlDataReader, vous découvrirez des tonnes de métadonnées revenant de la database.

Mon expérience est que si cela prend plus de 1 seconde pour terminer les instructions sql dans SSMS, vous obtenez probablement un problème de timeout d'attente dans le paramètre par défaut des applications Web. Cela arrive plus souvent dans les sélections que les insertions ou les mises à jour.

Mes solutions:

  1. Augmentez la valeur de timeout d'expiration dans web.config;
  2. Performance-affiner votre procédure stockée en utilisant le plan d'exécution;
  3. Évitez d'utiliser SqlDataReader. Utilisez SqlCommand pour insert et mettre à jour;
  4. Retournez comme le top 100 des loggings au lieu de tous les loggings si SqlDataReader doit être utilisé.