Ralentissement des performances de SqlDataReader

J'ai une requête en cours d'exécution ~ 2 secs dans MSSMS (returnnant 25K de lignes)

Même requête utilisée dans .NET (sqlReader) s'exprimant quelques minutes!

J'ai aussi essayé d'exécuter seulement le lecteur

(a commenté tout le code dans la boucle while en quittant reader.Read ()) – toujours le même!

Une idée de quoi?

Je voudrais configurer une trace dans SQL Server Profiler pour voir quels parameters d'options SET la connection utilise lors de la connection à partir du code .NET et quels parameters sont utilisés dans SSMS. Par SET parameters d'options, je veux dire

ARITHABORT ANSI_NULLS CONCAT_NULL_YIELDS_NULL //etc 

Jetez un oeil à MSDN pour une table d'options

J'ai déjà vu le problème où les options étaient différentes (dans ce cas, ARITHABORT ) et la différence de performance était énorme.

J'ai eu ce problème à. Cochez le paramètre "abandon arithmétique" dans les parameters de connection du server de database.

Je ne suis pas un administrateur de database et je n'ai pas le privilège de jouer avec Profiler – je vais requestr à mon administrateur de database et le laisser savoir.

En attendant, je suis remarqué boost de performances essentielles après l'ajout de " WITH RECOMPILE " param à SP Je parle

Donc, de mon sharepoint vue, il semble que ce soit le cas avec le plan d'exécution … Qu'en pensez-vous?

[EDIT] Aussi ce que j'ai vérifié effectuait une requête ci-dessous de QA et .NET

 select @@options 

Ma compréhension est qu'il doit returnner la même valeur pour les deux environnements. (Si pas differnet ex.plans sera utilisé) Ai-je raison?

[EDIT2] J'ai lu (à partir de http://www.sqldev.net/misc/fn_setopts.htm ) que ARITHABOIRT = ON dans QA (dans .NET il est éteint)

Est-ce que quelqu'un sait comment forcer ARITHABOIRT = ON pour chaque connection .NET?

Je vérifierais pour voir combien de time la récupération réelle prend.

par exemple:

  Private Sub timeCheck() 'NOTE: Assuming you have a sqlconnection object named conn 'Create stopwatch Dim sw As New System.Diagnostics.Stopwatch 'Setup query Dim com As New SqlClient.SqlCommand("QUERY GOES HERE", conn) sw.Start() 'Run query Dim dr As SqlClient.SqlDataReader = com.ExecuteReader() sw.Stop() 'Check the time Dim sql_query_time As Ssortingng = CStr((sw.ElapsedMilliseconds / 1000)) & " seconds" End Sub 

Cela vous permettra de voir si le hold-up est dans la récupération, ou dans l'exécution du lecteur.

Si vous exécutez le lecteur dans une boucle, où il s'exécute plusieurs fois, assurez-vous que vous utilisez CommandBehavior.CloseConnection

  SqlCommand cmd = new SqlCommand(); SqlDataReader rdr = cmd.ExecuteReader(CommandBehavior.CloseConnection) 

Si vous ne le faites pas, chaque fois que la boucle traite la ligne, quand elle se termine et que rdr et l'object de connection tombent hors de scope, l'object de connection ne sera pas explicitement fermé, il sera donc fermé et relâché dans le pool quand le Garbage Collector arrive enfin à le finaliser …

Ensuite, si votre boucle est assez rapide (ce qui est très probable), vous manquerez de connections. (Le pool a une limite maximum qu'il peut générer)

Cela entraînera une latence et des retards supplémentaires car le code continue de créer des connections supplémentaires inutiles (jusqu'au maximum) et d'attendre que le GC "rattrape" la boucle qui les utilise …

En outre, l'parsingur de requêtes ne télécharge pas le contenu complet du grand text ou des grands champs binarys. Votre SqlDataReader peut prendre plus de time car il télécharge le contenu complet.