Azure:.NET Framework(首先使用 EF 代码)和 Microsoft SQL Server 某些查询突然出现 CPU 峰值

Tu.*_*Ma. 2 .net c# sql-server entity-framework azure

我有一个在 Azure 中运行的应用程序。它有一个部署为应用服务的 .NET 框架 API,连接到 Microsoft Sql Server。.NET 框架应用程序使用实体框架代码优先来访问数据库。

通常,应用程序运行顺利。然而,有时一个端点会变得无响应(即需要几分钟才能返回答案)。此端点通过 EntityFramework 执行查询,并仅从数据库中检索一些数据点。这是针对 2 到 8 个传感器执行的代码(没有任何区别):

  List<Measurement> result = CreateContext().Measurements
                .Where(m => m.MeasurementSeries.SensorInfoID == sensorId)
                .Where(m => m.MeasurementSeries.StartTime <= toTime && m.MeasurementSeries.EndTime >= fromTime)
                .Where(m => m.Time > fromTime && m.Time <= toTime)
                .OrderByDescending(m => m.Time)
                .ToList();
Run Code Online (Sandbox Code Playgroud)

通过查看指标(也来自 ApplicationInsight),我发现没有执行奇怪的查询。我看到了预期的查询,并且数据库计算利用率跃升至 100%。

相同的查询,从相同的代码执行,连接到相同的远程数据库,但使用本地运行的 .NET Framework 应用程序,从数据库中花费不到一秒和不到 1% 的计算。当查询(最终)完成时,数据库计算利用率回到零。API 计算利用率非常低,始终如此。直接对数据库执行相同的 SQL 查询所需的时间不到一秒钟。

所有其他端点,其中一些对数据库进行更重的查询,工作正常。

我尝试从多个来源多次重新运行相同的查询,重新启动、停止和启动,重新部署应用程序。没发生什么事。上次,半天后,它才刚刚开始工作。这次已经过去一天了,什么都没有。

您是否有任何指向何处查找问题的指示?如果我可以提供更多信息,请告诉我,因为我可能没有考虑过它们,它也可以帮助我找出问题所在。

Tu.*_*Ma. 5

感谢@PrebenHuybrechts 在问题的评论中提供了解决它的工具。正如建议的那样,对于这样的问题,最好检查锁、等待统计信息和执行计划。

TL; 博士

Max DOP 设置为无限,考虑到我将 Sql Server 作为无服务器运行,从 2 个 vCore 扩展到 16 个 vCore,它不时对非常小的查询进行过度并行化。

以下工具可用于调试:sp_whoisactive、sp_BlitzWho。

长(er)版本

首先,我使用sp_whoisactive来查看在等待 API 响应时发生了什么。我调用了端点,然后运行

EXEC sp_WhoIsActive
    @get_task_info = 2
Run Code Online (Sandbox Code Playgroud)

在结果中,我发现了有罪的查询,挂起,wait_info状态为CXPACKET。从这篇文章我认为这CXPACKET意味着主进程正在等待从属进程完成处理,并且微软建议将 Max DOP(最大并行度)设置为 8。我这样做了使用 Microsoft SSMS,它的效果非常棒。

我猜想,考虑到在其他地方使用了相同的查询来检索大量数据,它正在针对该场景对其进行优化,使得查询仅检索少量数据点时速度很慢。