it-swarm-fr.com

TSQL: Trouvez des requêtes provoquant trop de compilations SQL et de recompilations SQL séparément

Je veux savoir ce qui cause les compilations hautes SQL (pas de re-compilations) que je constate dans les compteurs de surveillance de la performance.

Voici ma prise: Si je vois beaucoup de compilations SQL, cela signifie que les questions de notre système ne sont pas mises en cache pour des raisons suivantes:

  • Beaucoup de requêtes adhoc
  • Quertimes d'exécution que SQL ne cache pas par ex. :

    Mise à jour Table1 Set Col1 = 'String plus de 8 000 caractères .....' Où Key_Column = Certains int

  • Les plans sont timings et étant retirés du cache car: le cache est à court d'espace ou des plans ne sont pas utilisés assez longtemps.

La seule chose qui se trouve à proximité de capturer les inserts de cache dans le profileur est stockée des procédures stockées -> SP: cacheiserts, mais il ne s'occupe que de cache de procédure stockée.

J'ai donc essayé ce qui suit pour obtenir des requêtes adhoc:

SELECT [cp].[refcounts] -- when Refcounts becomes 0, plan is excluded from cache.
    , [cp].[usecounts] 
    , [cp].[objtype] 
    , st.[dbid] 
    , st.[objectid] 
    , st.[text] 
    , [qp].[query_plan] 
FROM sys.dm_exec_cached_plans cp     
CROSS APPLY sys.dm_exec_sql_text ( cp.plan_handle ) st     
CROSS APPLY sys.dm_exec_query_plan ( cp.plan_handle ) qp ;

Je pensais que les requêtes qui ont causé les compiles devraient être celles avec objtype = adhoc, mais cela pourrait également être concerné à la compilation. Maintenant, je dois exécuter le profileur, capturer des requêtes provoquant des re-compilations, puis l'exclude de la liste ci-dessus.

Est-ce que je vais dans la bonne direction?

Y a-t-il une seule requête puis-je utiliser pour faire des compilations SQL juste sans trop de travail?

Ressources qui m'a aidé à faire face à la connaissance ci-dessus:

http://social.msdn.microsoft.com/forums/en/sqldatabasegine/thread/954b4fba-3774-42fba-3774-42e3-86E7-E5172ABE0C8http://www.sqlteam.com/ forums/topic.asp? topic_id = 143946http://technet.microsoft.com/en-nz/library/cc966425 (fr-US) .aspx
[.____] http://www.sqlservercenter.com/forums/topic914951-360-1.aspx

Toute aide est vraiment appréciée.

8
Manjot

Je ne pense pas que vous puissiez trouver ceci par un moyen simple, mais il est possible de toute façon de passer cela. Profiler propose de nombreux types de classe d'événements pouvant être utilisés pour analyser les performances d'une requête. Démarrez une nouvelle session de profileur et vérifiez les événements suivants:

Performance: Performance statistics
Stored Procedures: RPC:Completed
TSQL: SQL:BatchCompleted
TSQL: SQL: BatchStarting

Vérifiez pour afficher toutes les colonnes et sélectionnez chacune des colonnes sous Performance: Statistiques de performance uniquement. Le reste des événements peut être laissé avec le paramètre par défaut.

Ensuite, sélectionnez Colonne Filtres et filtrez par Databasename et/ou LoginName/ApplicationName/Nom d'hôte, etc., si vous les connaissez. Le but est de limiter le nombre de lignes distalées dans le profileur et ne se concentrer que sur vos besoins.

Ensuite, appuyez sur Exécuter et laissez-le courir pendant un moment (2-3 min aussi longtemps que nécessaire). Analyser les résultats dissipés principalement à l'occasion: Statistiques de performance.

Si les statistiques de performance se produiront souvent que le plan d'une requête a été mis en cache pour la première fois, compilé, re-compilé ou expulsé de Planchache. À partir de mes connaissances si une requête ne dispose pas de son plan de requête dans le cache de plan - vous verrez 2 lignes de EXPERANCESTATIQUISTIQUES et suivi de SQL: Batchstarting , puis SQL: BatchCompélé . Cela signifie que le plan de requête a été compilé pour la première fois, mis en cache, puis la requête démarrée et complétée.

Recherchez les colonnes suivantes sous Statistiques de performance Événement:

SPID - ID of the session on which the event occurred. You can use it to identify the       
       row on SQL:BatchCompleted event which will display the SQL Query text and other  
       usefull information (Read/Writes, StartTime/EndTime)
Duration - Total time, in microseconds, spent during compilation.
EventSubClass - 0 = New batch SQL text that is not currently present in the cache.
                1 = Queries within a stored procedure have been compiled.
                2 = Queries within an ad hoc SQL statement have been compiled.
                3 = A cached query has been destroyed and the historical performance         
                    data associated with the plan is about to be destroyed.
                4 = A cached stored procedure has been removed from the cache and the  
                    historical performance data associated with it is about to be 
                    destroyed.

                5 = A cached trigger has been removed from the cache and the historical  
                    performance data associated with it is about to be destroyed.

Compte tenu du numéro d'événementsBlass, vous pouvez découvrir ce qui s'est passé avec le plan de requête et prendre des mesures spécifiques. De plus, vous pouvez ajouter d'autres colonnes à des procédures stockées et [~ # ~ ~] TSQL [~ # ~] CLASSES D'ÉVÉNEMENTS Si vous êtes interséqué dans le nom d'hôte, WindowsUser ou d'autres informations de la trace du profileur. De plus, la trace peut être stockée dans une table SQL rendant l'analyse plus facile et beaucoup plus personnalisable. Voici un Link décrivant plus la classe d'événement Statistiques de performance.

7
yrushka

Bien, voyons d'abord s'il y a une pression sur le cache.

select bpool_visible from sys.dm_os_sys_info
go

Multipliez ce nombre par 8 pour obtenir la mémoire dans K. 75% de celle-ci de 0 à 4g + 10% de celle-ci à partir de 4G-64g + 5% de plus est la limite de pression du cache . Si vous atteignez 75% de cette limite, SQL Server commencera à purger les plans du cache. Cette purge arrive lorsqu'un nouveau plan de requête est ajouté au cache, de sorte que le thread pause pour faire ce travail. La deuxième chose qui peut causer des plans à purger est si le nombre de plans dépasse 4 fois le nombre de godets de hachage (une table de hachage de plantage d'un plan_handle à un plan). Il y a 10 000 sur un système 32 bits et 40 000 sur un système 64 bits.

select type, sum(pages_allocated_count) as pages_used from sys.dm_os_memory_objects 
where type in ('MEMOBJ_CACHESTOREOBJCP', 'MEMOBJ_CACHESTORESQLCP', 'MEMOBJ_CACHESTOREXPROC')
group by type
go

La décision sur quoi de purge n'est pas faite sur l'utilisation, mais sur le coût du plan, les régimes les moins chers sont purgés d'abord (coût pour produire, ne pas exécuter). Vous pouvez voir cela si vous ajoutez les colonnes original_cost et current_cost à votre requête sur sys.dm_exec_cached_plans. Un plan ad hoc commence à 0 et est incrémenté de 1 chaque fois qu'il est utilisé. Lorsque la pression de cache se produit, SQL Server soustrait la moitié de chaque coût, puis purge ceux qui ont atteint 0.

Si vous avez beaucoup d'ad-hoc sql essayer:

exec sp_reconfigure 'optimize for ad hoc workloads', 1
go
reconfigure
go

Dans ce mode, SQL Server cache uniquement un "talon", environ 300 octets de taille (un plan de requête normal est minimum de 24 000), contenant un hachage et un pointeur au texte SQL, la première fois qu'il voit une instruction SQL particulière, puis Cachez ensuite le plan complet s'il est exécuté à nouveau. Cela ne sera pas nécessairement coupé sur des compilations en soi, mais il allumera la pression de la mémoire sur le cache du plan.

Remarque: cela fonctionne en 2008, pas essayé en 2005.

Un autre tour est

alter database ... set parameterization forced
go

Cela causera que SQL Server traite les constantes comme paramètres, ce qui peut aider à la fonctionnalité autoparamètre . Caches en cache généralement des états SQL similaires. AD-HOC SQL devrait avoir ses plans de requête en cache, à moins que votre serveur ne soit très court sur la mémoire, mais cela s'appuie sur des correspondances textuelles exactes, à moins que cela puisse être paramétré , auquel cas il se comporte plus comme une requête préparée.

4
Gaius

Avez-vous de nombreux emplois SQL Server sur cette boîte? Notez qu'en 2005, les requêtes du travail de l'agent ne sont pas mises en cache et peuvent également provoquer des compilations de cache BLOAT et SQL.

Regardez le nombre de plans avec des comptes à faible réutilisation. Ce sont vos coupables.

Certaines notes connexes sur la mise en cache de plan ci-dessous.

http://www.sqlskills.com/blogs/kimberly/post/plan-cache-adhoc-workloads-and-clearing-the-single-uuse-plan-cache-bloat.aspx

http://www.sqlskills.com/blogs/kimberly/post/clearing-the-cache-are-Ithere-other-Options.aspx

3
Sankar Reddy

Cet effet est appelé "pollution du plan de requête", où de nombreuses requêtes SQL similaires génèrent des plans d'exécution distincts mais équivalents.

Les requêtes ad hoc entraînent des frais généraux par analyse individuelle, mais généralement pas la pollution du plan de requête, car leurs plans ne sont pas stockés. Ceci est différent pour les requêtes avec un seul paramètre (sous SQL Server), ceux-ci seront traités comme une requête paramétrée.

Il existe des cas typiques pour la pollution du plan de requête:

  • SQL requêtes avec un seul paramètre littéral codé dur (comme 'Select ID, nom de la personne où id = 1234')
  • surtout s'il est utilisé avec des commandes/procédures stockées qui forcent la base de données à stocker le plan de requête, telles que "SP_PEPEXEC" ou SP_EXececuteSQL 'sous MSSQL (je pense "exécuter immédiatement" sous Oracle fonctionne de la même manière)
  • les requêtes partiellement paramétrées, avec une grande variance dans les valeurs littérales "codées durement codées", telles que "Select * de SocCerMatches SM où SM.Date>" et sm.date <? et Homeclubid = 5678 et GuestClubid = 1234 '. Celles-ci sauveront des plans de requête en raison des paramètres, mais créeront un nouveau plan de requête pour chaque Homeclub ou votre logiciel modifiés (esp. Les valeurs de date/heure sont une excellente occasion d'introduire des paramètres dans de nombreuses API de DB, lorsque les requêtes échouent en raison de la date différente locale. formats).
  • Une autre source de pollution du plan de requête peut être des cadres tels que Ado.net avec des pilotes insuffisants, en combinaison avec des valeurs de chaîne/(n) Varchark. Certaines implémentations/pilotes définiront la taille des paramètres à la longueur de la chaîne réelle, ce qui provoque un plan de requête séparé pour chaque longueur de paramètre de chaîne différente dans la requête. Les meilleures pratiques semblent être l'utilisation de la taille de champ maximale (par exemple Varcharchar (4000)) ou d'un pilote qui met une longueur correcte
0
Erik Hart