相关疑难解决方法(0)

Task.Run()和Task.Factory.StartNew()之间有什么区别

我有方法:

private static void Method()
{
    Console.WriteLine("Method() started");

    for (var i = 0; i < 20; i++)
    {
        Console.WriteLine("Method() Counter = " + i);
        Thread.Sleep(500);
    }

    Console.WriteLine("Method() finished");
}
Run Code Online (Sandbox Code Playgroud)

我想在一个新的Task中启动这个方法.我可以开始这样的新任务

var task = Task.Factory.StartNew(new Action(Method));
Run Code Online (Sandbox Code Playgroud)

或这个

var task = Task.Run(new Action(Method));
Run Code Online (Sandbox Code Playgroud)

但是Task.Run()和之间有什么区别吗Task.Factory.StartNew()?它们都使用ThreadPool并在创建Task的实例后立即启动Method().当我们应该使用第一个变体和第二个?

c# multithreading task-parallel-library

155
推荐指数
6
解决办法
8万
查看次数

HttpRequest在ASP.NET Core MVC中没有中止(取消)浏览器中止

我编写了以下MVC控制器来测试取消功能:

class MyController : Controller
{
    [HttpGet("api/CancelTest")]
    async Task<IActionResult> Get()
    {
        await Task.Delay(1000);
        CancellationToken token = HttpContext.RequestAborted;
        bool cancelled = token.IsCancellationRequested;
        logger.LogDebug(cancelled.ToString());
        return Ok();
    }
}
Run Code Online (Sandbox Code Playgroud)

说,我想取消请求,因此在上面的控制器操作中记录值' true '.如果服务器实现IHttpRequestLifetimeFeature,这可能是服务器端.幸运的是,Kestrel确实如此,这可以通过以下方式实现:

var feature = (IHttpRequestLifetimeFeature) HttpContext.Features[typeof(IHttpRequestLifetimeFeature)];
feature.Abort();
Run Code Online (Sandbox Code Playgroud)

但问题是我想在客户端取消请求.例如,在浏览器中.在ASP.NET MVC/WebApi的预核版本中,如果浏览器中止请求,则取消令牌将自动取消.示例:在Chrome中多次刷新页面.在chrome dev工具的"网络"选项卡中,您现在可以看到取消上一个(未完成的)请求.

问题是:在Kestrel上运行的ASP.NET Core中,我只能在日志中看到以下条目:

Microsoft.AspNetCore.Server.Kestrel.Internal.Networking.UvException:错误-4081 ECANCELED操作已取消

因此,来自浏览器的中止请求到达并由Kestrel网络服务器处理.但它不会影响控制器中HttpContext的RequestAborted属性,因为该方法仍会记录值' false '.

问题: 有没有办法中止/取消我的控制器方法,以便将HttpContext.RequestAborted属性标记为已取消?

也许我可以做一些订阅Kestrel的操作取消触发器并调用IHttpRequestLifetimeFeature.Abort()方法的东西?

更新: 我做了一些进一步的测试,看起来HttpRequest IS实际上已经中止,但在实际取消之前似乎有某种延迟.延迟不是时间因素,似乎直接来自libuv(Kestrel网络服务器构建在其上的库).我在https://github.com/aspnet/KestrelHttpServer/issues/1103上发布了更多信息

更多更新: 问题已移至另一个,因为前一个包含多个问题.https://github.com/aspnet/KestrelHttpServer/issues/1139

cancellation asp.net-core-mvc kestrel-http-server asp.net-core

14
推荐指数
1
解决办法
2594
查看次数

HttpContext.RequestAborted 和 CancellationToken 参数有什么区别?

我正在尝试为ASP.NET Core 2.0创建异步视图组件。当用户离开页面时,它会执行一个应该被取消的操作。我有以下选择:

  1. 使用 HttpContext.RequestAborted
  2. 使用 CancellationToken 参数
  3. 我也可以链接令牌

选项 1 如下所示:

public class AmazingMessageViewComponent : ViewComponent
{
    public async Task<IViewComponentResult> InvokeAsync(string text, int wait)
    {
        //uses request aborted
        await Task.Delay(wait, HttpContext.RequestAborted);
        return View<string>(text);
    }
}
Run Code Online (Sandbox Code Playgroud)

选项 2 如下所示:

public class AmazingMessageViewComponent : ViewComponent
{
    public async Task<IViewComponentResult> InvokeAsync(CancellationToken cancellationToken, string text, int wait)
    {
        await Task.Delay(wait, cancellationToken);
        return View<string>(text);
    }
}
Run Code Online (Sandbox Code Playgroud)

这两个操作都不适用于 Kestrel(看起来像一个错误)。在这两种情况下,都填充了令牌(可能是因为结构?)

有什么区别,我应该使用什么?

asp.net-mvc kestrel .net-core asp.net-core-viewcomponent

9
推荐指数
1
解决办法
4421
查看次数