异步组件在MVC 6中不起作用

时间:2015-05-04 18:39:19

标签: c# asynchronous asp.net-core-mvc

我正在尝试在MVC 6中实现异步组件,我正在努力解决它。

查看代码:

@await Component.InvokeAsync("GetTextA")
@Component.Invoke("GetTextB")

Compnent A Code:

public class GetTextAViewComponent : ViewComponent
{ 
    public async Task<IViewComponentResult> InvokeAsync()
    {
        await Task.Delay(12000);
        return View("Default","from code");
    }
}

组件B代码:

public class GetTextBViewComponent : ViewComponent
{ 
    public IViewComponentResult Invoke()
    {
        return View("Default");
    }
}

加载视图需要12000毫秒以上。这意味着同步加载异步组件。

如何使其异步加载,以便加载视图中的所有内容而无需等待异步组件。

2 个答案:

答案 0 :(得分:3)

如果您希望视图呈现并稍后运行异步代码,则基本上必须使用Ajax。运行组件异步意味着它不会阻塞线程,并且可以被其他请求重用。

编辑: 如果您想渲染页面的顶部,并且稍后显示其余部分,则可以使用新的@Flush功能。在长时间运行的任务之前添加对@await FlushAsync()的调用,并且视图的顶部将刷新到客户端。如果您正在使用布局,它会变得有点复杂,请按照此测试获取更多示例:

https://github.com/aspnet/Mvc/tree/9ea535027153094d547c2c001999b16a2598fbac/test/WebSites/RazorWebSite/Views/FlushPoint

答案 1 :(得分:1)

在下面的示例中,您可以看到尽管两个组件都有6秒的延迟,但渲染响应不需要12秒。这证明,可以异步调用视图组件,这有效地节省了CPU时钟周期,并使其提供比以往更多的同时请求。

AViewComponent

    public async Task<IViewComponentResult> InvokeAsync()
    {
        await Task.Delay(6000);
        return View<string>("Hello World A!");
    }

BViewComponent

    public async Task<IViewComponentResult> InvokeAsync()
    {
        await Task.Delay(6000);
        return View<string>("Hello World B!");
    }

视图\共享\组件\ A \ Default.cshtml

@model string

<h1>@Model</h1>

视图\共享\组件\ B \ Default.cshtml

@model string

<h1>@Model</h1>

index.cshtml

@DateTime.Now

@{ 
    var taskA = Component.InvokeAsync("A");
    var taskB = Component.InvokeAsync("B");

    taskA.Wait();
    taskB.Wait();
}

@taskA.Result
@taskB.Result

@DateTime.Now

输出(参见6秒的时差)

  

2016/6/14 6:09:04

     

Hello World A!

     

Hello World B!

     

2016/6/14 6:09:10