ASP.Net Core API响应花费太多时间

问题描述 投票:0回答:1

我有一个具有9000行和97列的SQL数据库表。它的主键有2列:ColorName。您可以看到简化表以更好地成像:

“在此处输入图像描述”

我有一个ASP.NET Core API监听URL api/color/{colorName},它读取表以获取颜色信息。目前,我有3种颜色,每种颜色约有3000行。

需要太多时间。它在2383ms内读取表,并在14ms内映射到DTO。之后,我立即将DTO返回给使用者,但API花费了4135.422毫秒。我不明白为什么。我想我应该花2407.863毫秒,但不是。花费将近2倍。

您可以在下面查看我的代码和日志。您是否知道如何改善响应时间?

我使用Entity Framework Core 3.1,AutoMapper和ASP.NET Core 3.1。

服务:

public async Task<IEnumerable<ColorDTO>> GetColors(string requestedColor)
{
    var watch = System.Diagnostics.Stopwatch.StartNew();
    var colors = await _dbContext.Colors.Where(color => color.color == requestedColor).ToListAsync();
    watch.Stop();
    _logger.LogError("Color of:{requestedColor} Reading takes:{elapsedMs}", requestedColor, watch.ElapsedMilliseconds);


    var watch2 = System.Diagnostics.Stopwatch.StartNew();
    var colorDtos = _mapper.Map<IEnumerable<ColorDTO>>(colors);
    watch2.Stop();
    _logger.LogError("Color of:{requestedColor} Mapping takes:{elapsedMs}", requestedColor, watch2.ElapsedMilliseconds);

    return colorDtos;
}

控制器:

public async Task<ActionResult<IEnumerable<ColorDTO>>> GetBlocksOfPanel(string requestedColor)
{
    return Ok(await _colorService.GetColors(requestedColor));
}

和日志:

2020-04-27 15:21:54.8793||0HLVAKLTJO59T:00000003|MyProject.Api.Services.IColorService|INF|Color of Purple Reading takes:2383ms
2020-04-27 15:21:54.8994||0HLVAKLTJO59T:00000003|MyProject.Api.Services.IColorService|INF|Color of Purple Mapping takes:14ms
2020-04-27 15:21:54.9032||0HLVAKLTJO59T:00000003|Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker|INF|Executed action method MyProject.Api.Web.Controllers.ColorsController.GetColors (MyProject.Api.Web), returned result Microsoft.AspNetCore.Mvc.OkObjectResult in 2407.863ms.
2020-04-27 15:21:54.9081||0HLVAKLTJO59T:00000003|Microsoft.AspNetCore.Mvc.Infrastructure.ObjectResultExecutor|INF|Executing ObjectResult, writing value of type 'System.Collections.Generic.List`1[[MyProject.Api.Contracts.Dtos.ColorDTO, MyProject.Api.Contracts, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null]]'.
2020-04-27 15:21:56.4895||0HLVAKLTJO59T:00000003|Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker|INF|Executed action MyProject.Api.Web.Controllers.ColorsController.GetColors (MyProject.Api.Web) in 4003.8022ms
2020-04-27 15:21:56.4927||0HLVAKLTJO59T:00000003|Microsoft.AspNetCore.Routing.EndpointMiddleware|INF|Executed endpoint 'MyProject.Api.Web.Controllers.ColorsController.GetColors (MyProject.Api.Web)'
2020-04-27 15:21:56.4972||0HLVAKLTJO59T:00000003|Microsoft.AspNetCore.Hosting.Diagnostics|INF|Request finished in 4135.422ms 200 application/json; charset=utf-8
c# api asp.net-core
1个回答
0
投票

正如@ejwill在他的评论中提到的那样,您需要在整个操作中考虑延迟。从数据库获取并映射到DTO只是请求和对API的往返过程中发生的一部分。

您可以通过此处的一些优化来减少对数据库表的查询时间。您无需指明正在使用的数据库,但是基于两个字符串/ varchar值的复合键可能不一定是性能最高的,并且在要过滤的值上使用索引也可能会有所帮助-权衡取舍,取决于您是针对写入还是针对读取进行优化。话虽这么说,但97列都不是不重要的。您是否需要通过API查询并返回所有97列?分页是一种选择吗?

如果必须一次返回所有97列的所有数据,并且要频繁查询API,则还可以考虑使用内存中的缓存,尤其是在表不经常更改的情况下;您不必每次都往返数据库,而是将数据副本保存在内存中,以便可以更快地返回数据。您可以查看内存缓存的实现,该缓存支持世代模型以在获取新版本时继续提供数据。

https://github.com/jfbosch/recache

© www.soinside.com 2019 - 2024. All rights reserved.