【发布时间】:2019-10-23 01:32:32
【问题描述】:
有时,SQL Azure 会导致存储过程中的简单查询需要很长时间才能运行。经过大量研究,我已将问题跟踪到查询存储中的 last_optimize_duration 显示 20 多秒。
我已经以多种方式重写了查询,简化了它,使用了索引,尝试从主要的存储过程中调用其他存储过程。查询本身似乎在 100% 的时间内运行得很快,但有时系统重新编译它时除外。当然,如果我在 SSMS 中执行此操作,它会快速编译并运行。
CREATE PROC[dbo].spLogHatesMe(
@CID[VARCHAR](200),
@LogType VARCHAR(50) = NULL
)
AS
SELECT *
FROM dbo.Log
WHERE CID = @CID
AND LogType = @LogType;
GO
还请注意,日志表在 CID 和 LogType 上有一个索引。
我希望优化时间与 1000-5000 微秒范围内的所有其他编译类似。不是“25913462”,这是我最后的持续时间。没有其他查询存在相同类型的问题。
Log表是一个以insert为主的日志表。对于一项特定任务,我们需要回顾并阅读其中一个值。大约,每 1 次读取 20-25 次插入。
我正在使用查询存储之外的这个查询来获取编译时间:
SELECT TOP 100 *
FROM sys.query_store_plan AS Pl
INNER JOIN sys.query_store_query AS Qry ON Pl.query_id = Qry.query_id
INNER JOIN sys.query_store_query_text AS Txt ON Qry.query_text_id = Txt.query_text_id
WHERE Qry.is_internal_query=0
ORDER BY Pl.last_compile_start_time desc
【问题讨论】:
-
我的第一个猜测是长编译是需要更新一个或多个列的统计信息的地方
-
@MartinSmith 使用 sys.dm_db_stats_properties 并检查时间与 sys.query_store* 值,看起来统计信息在查询问题前一小时左右更新。不过我可能看的不太清楚。
-
@DavidMack 但是更新统计信息时不会重新编译查询。它们被标记为重新编译,直到下次查询运行时才会发生。您不能使用 stats 属性来确定重新编译发生的时间。
-
@AaronBertrand 和 Martin Smith,我正在查看错误的时间戳(该死的 UTC)。 stat 的更新和存储的 proc 的编译时间大致相同: Compile: 13:39:42 vs Stats:13:40:08 相差 26 秒,大约等于延迟时间 I有经验的。那么问题是,我该如何解决它?我应该只禁用该表上的自动更新统计信息吗?
标签: sql sql-server optimization