Sqlserver
 sql >> Base de Dados >  >> RDS >> Sqlserver

Configurações com escopo de banco de dados SQL Server e correção automática de plano


Neste artigo, examinaremos as configurações com escopo do banco de dados e a correção automática do plano do SQL Server 2017. A Microsoft adicionou novos recursos ao SQL Server 2017 que melhoraram o desempenho da consulta.

O desempenho da consulta do SQL Server está relacionado à qualidade e precisão do plano de execução. Quando executamos uma consulta, o otimizador de consulta analisa muitos planos de execução e, em seguida, decide sobre o plano de execução de consulta ideal.

Estimativa de cardinalidade herdada: O Estimador de Cardinalidade prevê quantas linhas a consulta retornará, bem como determina a alocação de memória da consulta.

No SQL Server 2017, a versão padrão do modelo de estimativa de cardinalidade é 14.0, mas se você quiser usar a versão 7.0 mais antiga do Estimador de cardinalidade, poderá fazer isso alterando a opção Estimativa de cardinalidade herdada nas Configurações de escopo do banco de dados forte> seção.

O valor padrão da Estimativa de Cardinalidade Legacy é OFF. Assim, se você quiser usar a versão mais antiga, você deve ligá-la.



Como alternativa, você pode alterar essa propriedade no T-SQL.
ALTER DATABASE SCOPED CONFIGURATION SET LEGACY_CARDINALITY_ESTIMATION =OFF|ON;

No entanto, se você habilitar essa configuração, ela afetará todas as consultas. Como resultado, isso pode prejudicar o desempenho da consulta. Para evitar isso, você pode usar a dica FORCE_LEGACY_CARDINALITY_ESTIMATION.

Quando executarmos essa consulta no banco de dados WideWorldImporters, ela usará automaticamente uma nova versão da estimativa de cardinalidade.
SELECT [o].[CustomerID], o.LastEditedBy , [o].[OrderDate] FROM Sales.Orders oWHERE [o].[OrderDate]>='20140101'



Quando adicionamos FORCE_LEGACY_CARDINALITY_ESTIMATION à consulta, o otimizador de consulta usará a versão anterior ou mais antiga da estimativa de cardinalidade.





MAXDOP : podemos definir o grau máximo de paralelismo para um banco de dados individual. Antes da criação desse recurso, só podíamos configurar o nível do servidor MAXDOP.

A dica de consulta MAXDOP nos permite executar consultas em paralelo.
ALTER DATABASE SCOPED CONFIGURAÇÃO SET MAXDOP =4; IR



Sniffing de parâmetros: Quando o tempo de execução de uma consulta muda drasticamente e essa mudança de tempo está relacionada ao parâmetro de consulta, ela é chamada de sniffing de parâmetro.

Agora, vamos criar um procedimento armazenado no banco de dados AdventureWorks. Enviaremos diferentes parâmetros e compararemos os planos de execução.
DROP PROCEDURE SE EXISTE Get_OrdersGOCREATE PROCEDURE Get_Orderes@ProductID INTASSELECT SalesOrderDetailID, OrderQtyFROM Sales.SalesOrderDetailWHERE ProductID =@ProductID;GO/********Não use este script em servidores de produção!********/ DBCC FREEPROCCACHE--Consulta MarsEXEC Get_OrderID_OrderQty @ProductID=870DBCC FREEPROCCACHE--Consulta VenusEXEC Get_OrderID_OrderQty @ProductID=897

Conforme mostrado na imagem abaixo, o SQL Server gera um plano de execução diferente para a mesma consulta. O plano de execução do Query Mars recomenda um índice. O parâmetro de consulta altera o plano de execução ideal.



Execute esta consulta e observe os planos de execução.
DBCC FREEPROCCACHE--Consulta MarsEXEC Get_OrderID_OrderQty @ProductID=870--Consulta VenusEXEC Get_OrderID_OrderQty @ProductID=897





O plano de execução do Query Venus é o mesmo que o plano de execução do Query Mars. Este é o parâmetro sniffing porque o plano de execução em cache é compilado para o plano de execução Query Mars. Por esse motivo, o Query Venus usa o mesmo plano de execução.

Agora, desabilitaremos o sniffing de parâmetros e executaremos as mesmas consultas.
ALTER DATABASE SCOPED CONFIGURATION SET PARAMETER_SNIFFING =OFF;DBCC FREEPROCCACHE--Consulta MarsEXEC Get_OrderID_OrderQty @ProductID=870--Consulta VenusEXEC Get_OrderID_OrderQty @ProductID=897

Vamos examinar:



O otimizador do SQL Server Query gerou o plano de execução ideal para Query Venus e Query Mars. Essa abordagem fornece o desempenho ideal para a consulta.

Existem algumas opções para evitar esse problema:
  • OPÇÃO(RECOMPILAR)
  • OPÇÃO (OTIMIZAR PARA(@VARIABLE=UNKNOWN))

Correção automática do plano


O SQL Server 2017 inclui um novo recurso chamado Correção Automática de Plano. Quando executamos uma consulta, o otimizador de consultas cria um plano de execução. Por alguns motivos, o otimizador de consulta escolhe planos de execução errados. Algumas das razões são as seguintes:
  • Uma consulta que não atende aos critérios de desempenho
  • Estatísticas desatualizadas
  • Índices inadequados

Quando o otimizador de consulta do SQL Server decide alterar o plano de execução e esse plano de execução prejudica o desempenho, o desempenho da consulta é chamado de regressão do plano. Um novo recurso vem com o SQL Server 2016. Essa ferramenta ajuda no monitoramento e solução de problemas de desempenho da consulta e, ao mesmo tempo, armazena métricas de desempenho e contadores da execução da consulta.

Podemos habilitar essas opções nas propriedades do banco de dados.



Agora, vamos fazer uma demonstração desse recurso. Antes de tudo, limpe o cache do procedimento e crie um procedimento armazenado.
/**************************************** Não use este script em servidores de produção********************************************/USE WideWorldImportersALTER DATABASE WideWorldImporters SET QUERY_STORE =LIGADO; ALTER DATABASE [WideWorldImporters] SET QUERY_STORE CLEAR ALLDBCC FREEPROCCACHE --Este comando limpará todo o cache de procedimento no SQL Server. Não tente no ambiente de produção-- ALTER DATABASE WideWorldImporters SET AUTOMATIC_TUNING (FORCE_LAST_GOOD_PLAN =OFF); DROP PROCEDURE IF EXISTS Test_CoddingSight2 GO CREATE PROC Test_CoddingSight2 @Id AS INT AS selecione soma([UnitPrice]*[Quantity]) de Sales.OrderLines O INNER JOIN sales.Orders o1 ON o1.OrderID =o.OrderID onde o.PackageTypeID =@ Código

Nesta etapa, executaremos este procedimento com diferentes parâmetros e encontraremos a diferença de tempo de execução.
--Consulta AlphaDBCC FREEPROCCACHE EXEC Test_CoddingSight2 7GO 80DBCC FREEPROCCACHE EXEC Test_CoddingSight2 -1--Consulta BetaEXEC Test_CoddingSight2 7GO 80

Como você pode ver, a primeira consulta foi concluída em 12 segundos, enquanto a segunda foi feita em 33 segundos. A razão para essa diferença dramática é que o otimizador de consulta escolhe um plano de execução inadequado para o Query Beta.

Vamos comparar os planos de execução do Query Alpha e do Query Beta.

Plano de execução do Query Alpha



Plano de execução da Consulta Beta



Nas imagens acima, o otimizador de consultas cria diferentes planos de execução para a mesma consulta. Quando analisamos os Principais recursos que consomem consultas , podemos ver que o Query Beta consome mais recursos do que o Query Alpha.



A consulta abaixo retornará informações detalhadas sobre as recomendações de ajuste.
SELECT nome, motivo, pontuação,JSON_VALUE(detalhes, '$.implementationDetails.script') como script, detalhes.* FROM sys.dm_db_tuning_recommendations CROSS APPLY OPENJSON(details, '$.planForceDetails') WITH ( query_id int '$ .queryId', regressed_plan_id int '$.regressedPlanId', last_good_plan_id int '$.recommendedPlanId') como detalhesWHERE JSON_VALUE(state, '$.currentValue') ='Active'



A coluna do motivo mostra por que devemos aplicar essa recomendação.

Agora, executaremos novamente o Query Alpha e o Query Beta com a correção automática do plano habilitada.
/**************************************** Não use este script em servidores de produção********************************************/ALTER DATABASE [WideWorldImporters] SET QUERY_STORE CLEAR ALLDBCC FREEPROCCACHE /****************************************Ativar correção automática do plano *****************************************/ALTER DATABASE WideWorldImporters SET AUTOMATIC_TUNING (FORCE_LAST_GOOD_PLAN =EM); --Consulta AlphaDBCC FREEPROCCACHE EXEC Test_CoddingSight2 7GO 80DBCC FREEPROCCACHE EXEC Test_CoddingSight2 -1--Consulta BetaEXEC Test_CoddingSight2 7GO 80

Após esta demonstração, o plano de execução do Query Alpha é aplicado ao Query Beta. Além disso, os tempos de execução do Query Alpha e do Query Beta são próximos um do outro. A consulta abaixo retornará o status de correção automática do plano.
SELECT nome, motivo, pontuação,JSON_VALUE(estado, '$.currentValue') como status,JSON_VALUE(detalhes, '$.implementationDetails.script') como script, detalhes.* FROM sys.dm_db_tuning_recommendations CROSS APPLY OPENJSON(detalhes , '$.planForceDetails') WITH ( query_id int '$.queryId', regressed_plan_id int '$.regressedPlanId', last_good_plan_id int '$.recommendedPlanId') as detailsWHERE JSON_VALUE(state, '$.currentValue') ='Verificando' 


Além disso, podemos encontrar algumas informações gráficas em Consultas com planos forçados . Este gráfico define os planos de consulta forçada e a consulta.



Referências

Correção automática do plano no SQL Server 2017

Estimativa de cardinalidade