异步VS MVC的控制器问题基准同步 [英] Async vs Sync Benchmarks on MVC Controller with Questions

查看:141
本文介绍了异步VS MVC的控制器问题基准同步的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我已经设置了的例子从这个MSDN文章的使用异步方法在ASP.NET MVC 4 ,并做了一些基准测试,看看我想出。

服务器配置:


  • Windows 7专业版(64位)

  • IIS 7.5

  • 英特尔酷睿i7-2600S @ 2.80HGz

  • 8GB内存

  • 程序池>最大工作进程:10

我设置了​​2个控制器同步异步和使用基准装载机工具做了一些测试。装载机工具只是发出一分钟50-60不变的请求。每个控制器都调用相同的web服务的3倍。在code语言为每个低于:


SYNC:

 公众的ActionResult同步()
{
    变种G1 = GetGizmos(URL1);
    变种G2 = GetGizmos(URL2);
    变种G3 = GetGizmos(URL3);
    返回内容();
}公共对象GetGizmos(字符串URI)
{
    使用(Web客户端Web客户端=新的WebClient())
    {
        返回JsonConvert.DeserializeObject(
         webClient.DownloadString(URI)
        );
    }
}

ASYNC:

 公共异步任务<&的ActionResult GT;异步()
{
    变种G1 = GetGizmosAsync(URL1);
    变种G2 = GetGizmosAsync(URL2);
    变种G3 = GetGizmosAsync(URL3);
    VAR A1 =等待G1;
    VAR A2 =等待G2;
    VAR A3 =等待G3;
    返回内容();
}
公共异步任务<对象> GetGizmosAsync(字符串URI)
{
    使用(HttpClient的HttpClient的=新的HttpClient())
    {
        变种响应=等待httpClient.GetAsync(URI);
        返回(等待response.Content.ReadAsAsync<对象>());
    }
}

第一个问题,有没有人知道为什么异步所用的时间,更少的运行,造成超时,而同步的版本是不是?我想使用异步因为这将是更快,没有超时等只是看起来不正确,我在这里做得不对?可以做些什么来改善/解决它?

第二个问题,在一般使用WebRequests,是有办法,加快了吗?我已经设置了以下在我的的Global.asax ,但仍不能确定,如果用法是正确的:

  System.Net.ServicePointManager.DefaultConnectionLimit = 1000;

此外,任何其他建议,以帮助加快执行这类tasts的应用将是非常有益的。


解决方案

我认为,线索是在比较

  webClient.DownloadString(URI)

  VAR响应=等待httpClient.GetAsync(URI);
返回(等待response.Content.ReadAsAsync<对象>());

也许你可以尝试

  webclient.DownloadStringAsync(URI)

,你可以优化您的异步code到

 等待Task.Run(()=> {
    //只是运行您的同步code在这里
    变种G1 = GetGizmos(URL1);
    变种G2 = GetGizmos(URL2);
    变种G3 = GetGizmos(URL3);
    返回内容();
});

有足够的有一个异步屈服点这里。

请参考此答案约异步细节: Do你必须把Task.Run的方法,使之异步?

I have set-up the examples from this MSDN article Using Asynchronous Methods in ASP.NET MVC 4 and have done some benchmarking to see what I come up with.

Server Configuration:

  • Windows 7 Professional (x64)
  • IIS 7.5
  • Intel Core i7-2600S @ 2.80HGz
  • 8GB Memory
  • AppPool > Maximum Worker Processes: 10

I set-up 2 controllers Sync and Async and did some testing using a loader tool for benchmarking. The loader tool just sends 50-60 constant requests for one minute. Each controller is calling the same webservice 3 times. The code for each is below:


SYNC:

public ActionResult Sync()
{
    var g1 = GetGizmos("url1");
    var g2 = GetGizmos("url2");
    var g3 = GetGizmos("url3");
    return Content("");
}

public object GetGizmos(string uri)
{
    using (WebClient webClient = new WebClient())
    {
        return JsonConvert.DeserializeObject(
         webClient.DownloadString(uri)
        );
    }
}

ASYNC:

public async Task<ActionResult> Async()
{
    var g1 = GetGizmosAsync("url1");
    var g2 = GetGizmosAsync("url2");
    var g3 = GetGizmosAsync("url3");
    var a1 = await g1;
    var a2 = await g2;
    var a3 = await g3;  
    return Content("");
}


public async Task<object> GetGizmosAsync(string uri)
{            
    using (HttpClient httpClient = new HttpClient())
    {
        var response = await httpClient.GetAsync(uri);
        return (await response.Content.ReadAsAsync<object>());
    }
}

First question, does anyone know why Async is taking longer, running less and causing timeouts, whereas sync version isn't? I would think using Async for this would be faster, no timeouts, etc. Just doesn't seem right, am I doing something wrong here? What can be done to improve/fix it?

Second question, Using WebRequests in general, is there a way to speed that up? I have set the following in my global.asax but still unsure if the usage is correct:

System.Net.ServicePointManager.DefaultConnectionLimit = 1000;

Also, any other suggestions to help speed up an application performing these types of tasts will be very helpful.

解决方案

I think the clue is in your comparison

webClient.DownloadString(uri)

to

var response = await httpClient.GetAsync(uri);
return (await response.Content.ReadAsAsync<object>());

maybe you can try

webclient.DownloadStringAsync(uri)

and you could optimize your async code to

await Task.Run(() => {
    // just run your sync code here
    var g1 = GetGizmos("url1");
    var g2 = GetGizmos("url2");
    var g3 = GetGizmos("url3");
    return Content("");
});

It is enough to have one async yielding point here.

Refer to this answer for details about async: Do you have to put Task.Run in a method to make it async?

这篇关于异步VS MVC的控制器问题基准同步的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆