需要帮助的HttpClient的和WebClient的决定 [英] Need help deciding between HttpClient and WebClient
问题描述
我们的Web应用程序是运行在.Net框架4.0。用户界面通过调用Ajax调用控制器方法。
我们需要从我们的供应商消费REST服务。我正在评估调用REST服务在.NET 4.0中的最佳途径。 REST服务,需要基本身份验证方案,并
可以返回的XML和JSON数据。有上传/下载庞大的数据中没有要求,我看不到未来的任何东西。我看了看几个开源$ C $ C项目REST消费,并没有发现这些任意值来证明该项目的其他依赖。开始评估 Web客户端
和的HttpClient
。我下载的HttpClient对于.NET 4.0的的NuGet。
我搜索 Web客户端
和的HttpClient
和 提到,单个HttpClient的可以处理并发呼叫,它可以重复使用解析的DNS,饼干配置和验证这个网站。我还没有看到,我们可能会由于获得对差异的实用价值。
我做了一个快速的性能测试,以找到如何 Web客户端
(同步调用),的HttpClient
(同步和异步)演出。这里是结果:
使用相同的的HttpClient
实例的所有请求(最小 - 最大)
Web客户端同步:8毫秒 - 167毫秒
HttpClient的同步:3毫秒 - 7228毫秒
HttpClient的异步:985 - 10405毫秒
使用新的的HttpClient
为每个请求(最小 - 最大)
Web客户端同步:4毫秒 - 297毫秒
HttpClient的同步:3毫秒 - 7953毫秒
HttpClient的异步:1027 - 10834毫秒
code
公共类AHNData
{
公众诠释我;
公共字符串str;
}
公共类节目
{
公共静态HttpClient的HttpClient的=新的HttpClient();
私人静态只读字符串_url =HTTP://本地主机:9000 / API /价值/;
公共静态无效的主要(字串[] args)
{
#地区的跟踪
Trace.Listeners.Clear();
TextWriterTraceListener会twtl =新TextWriterTraceListener会(
C:\\ \\温度REST_Test.txt);
twtl.Name =TextLogger;
twtl.TraceOutputOptions = TraceOptions.ThreadId | TraceOptions.DateTime;
ConsoleTraceListener CTL =新ConsoleTraceListener(假);
ctl.TraceOutputOptions = TraceOptions.DateTime;
Trace.Listeners.Add(twtl);
Trace.Listeners.Add(CTL);
Trace.AutoFlush = TRUE;
#endregion
INT BATCHSIZE = 1000;
ParallelOptions parallelOptions =新ParallelOptions();
parallelOptions.MaxDegreeOfParallelism = BATCHSIZE;
ServicePointManager.DefaultConnectionLimit = 1000000;
的Parallel.For(0,BATCHSIZE,parallelOptions,
J =>
{
秒表SW1 = Stopwatch.StartNew();
GetDataFromHttpClientAsync<列表< AHNData>>(SW1);
});
的Parallel.For(0,BATCHSIZE,parallelOptions,
J =>
{
秒表SW1 = Stopwatch.StartNew();
GetDataFromHttpClientSync<列表< AHNData>>(SW1);
});
的Parallel.For(0,BATCHSIZE,parallelOptions,
J =>
{
使用(Web客户端的客户端=新的Web客户端())
{
秒表SW = Stopwatch.StartNew();
byte []的ARR = client.DownloadData(_url);
sw.Stop();
Trace.WriteLine(Web客户端同步+ sw.ElapsedMilliseconds);
}
});
Console.Read();
}
公共静态牛逼GetDataFromWebClient< T>()
{
使用(VAR Web客户端=新的Web客户端())
{
webClient.BaseAddress = _url;
返回JsonConvert.DeserializeObject< T>(
webClient.DownloadString(_url));
}
}
公共静态无效GetDataFromHttpClientSync< T>(秒表SW)
{
HttpClient的HttpClient的=新的HttpClient();
VAR响应= httpClient.GetAsync(_url)。结果;
VAR OBJ = JsonConvert.DeserializeObject< T>(
response.Content.ReadAsStringAsync()结果)。
sw.Stop();
Trace.WriteLine(HttpClient的同步+ sw.ElapsedMilliseconds);
}
公共静态无效GetDataFromHttpClientAsync< T>(秒表SW)
{
HttpClient的HttpClient的=新的HttpClient();
VAR响应= httpClient.GetAsync(_url).ContinueWith(
(一)=> {
JsonConvert.DeserializeObject< T>(
a.Result.Content.ReadAsStringAsync()结果)。
sw.Stop();
Trace.WriteLine(HttpClient的异步+ sw.ElapsedMilliseconds);
},TaskContinuationOptions.None);
}
}
}
我的问题
- 的REST调用返回3-4s这是可以接受的。呼叫休息 服务在其中被从调用控制器方法启动 Ajax调用。首先,调用在不同的线程运行, 不会阻止用户界面。所以,我能带同步调用坚守?
- 在上面的code是在localbox的我跑。在督促设置,DNS和代理
查找将参与其中。有没有使用任何优势
的HttpClient
在Web客户端
? - 是
的HttpClient
并发比Web客户端
更好?从测试结果来看,我看Web客户端
同步调用有更好的表现。 - 威尔
的HttpClient
是一个更好的设计选择,如果我们升级到.NET 4.5?性能是关键的设计因素。
我住在这两个F#和Web API的世界。
有很多的好东西发生在Web API,特别是在安全性消息处理程序等。
的形式我知道我只有一个意见,但我只推荐使用的HttpClient
为今后的任何工作。也许有一些方法来利用一些其他的作品走出 System.Net.Http
而不直接使用该程序集,但我无法想象如何将工作在这个时候。
说起比较这两个
- 在HttpClient的比Web客户端更接近于HTTP。
- 的HttpClient并不意味着完全取代Web客户端的,因为有像报告进展情况,自定义的URI方案,使FTP调用Web客户端提供 - 但HttpClient的不
如果您使用的是.NET 4.5,请不要使用异步善良与HttpClient的,微软提供给开发商。 HttpClient的是非常对称的HTTP那些Htt的prequest和Htt的presponse。
服务器端的弟兄更新:5理由使用新的HttpClient API
强类型头。 共享缓存,cookie和证书 访问饼干和共享饼干 控制缓存与共享缓存。 注入你code模块插入到ASP.NET管道。清洁和模块化code。
参考
C#5.0约瑟夫阿尔巴哈利
(Channel9的 - 视频生成2013)
五大理由使用新的HttpClient API连接到Web服务一>
Our web app is running in .Net Framework 4.0. The UI calls controller methods through ajax calls.
We need to consume REST service from our vendor. I am evaluating the best way to call REST service in .Net 4.0. The REST service requires Basic Authentication Scheme and it
can return data in both XML and JSON. There is no requirement for uploading/downloading huge data and I don't see anything in future. I took a look at few open source code projects for REST consumption and didn't find any value in those to justify additional dependency in the project. Started to evaluate WebClient
and HttpClient
. I downloaded HttpClient for .Net 4.0 from NuGet.
I searched for differences between WebClient
and HttpClient
and this site mentioned that single HttpClient can handle concurrent calls and it can reuse resolved DNS, cookie config and authentication. I am yet to see practical values that we may gain due to the differences.
I did a quick performance test to find how WebClient
(sync calls), HttpClient
(sync and async) perform. and here are the results:
Using same HttpClient
instance for all the requests (min - max)
WebClient sync: 8 ms - 167 ms
HttpClient sync: 3 ms - 7228 ms
HttpClient async: 985 - 10405 ms
Using a new HttpClient
for each request (min - max)
WebClient sync: 4 ms - 297 ms
HttpClient sync: 3 ms - 7953 ms
HttpClient async: 1027 - 10834 ms
Code
public class AHNData
{
public int i;
public string str;
}
public class Program
{
public static HttpClient httpClient = new HttpClient();
private static readonly string _url = "http://localhost:9000/api/values/";
public static void Main(string[] args)
{
#region "Trace"
Trace.Listeners.Clear();
TextWriterTraceListener twtl = new TextWriterTraceListener(
"C:\\Temp\\REST_Test.txt");
twtl.Name = "TextLogger";
twtl.TraceOutputOptions = TraceOptions.ThreadId | TraceOptions.DateTime;
ConsoleTraceListener ctl = new ConsoleTraceListener(false);
ctl.TraceOutputOptions = TraceOptions.DateTime;
Trace.Listeners.Add(twtl);
Trace.Listeners.Add(ctl);
Trace.AutoFlush = true;
#endregion
int batchSize = 1000;
ParallelOptions parallelOptions = new ParallelOptions();
parallelOptions.MaxDegreeOfParallelism = batchSize;
ServicePointManager.DefaultConnectionLimit = 1000000;
Parallel.For(0, batchSize, parallelOptions,
j =>
{
Stopwatch sw1 = Stopwatch.StartNew();
GetDataFromHttpClientAsync<List<AHNData>>(sw1);
});
Parallel.For(0, batchSize, parallelOptions,
j =>
{
Stopwatch sw1 = Stopwatch.StartNew();
GetDataFromHttpClientSync<List<AHNData>>(sw1);
});
Parallel.For(0, batchSize, parallelOptions,
j =>
{
using (WebClient client = new WebClient())
{
Stopwatch sw = Stopwatch.StartNew();
byte[] arr = client.DownloadData(_url);
sw.Stop();
Trace.WriteLine("WebClient Sync " + sw.ElapsedMilliseconds);
}
});
Console.Read();
}
public static T GetDataFromWebClient<T>()
{
using (var webClient = new WebClient())
{
webClient.BaseAddress = _url;
return JsonConvert.DeserializeObject<T>(
webClient.DownloadString(_url));
}
}
public static void GetDataFromHttpClientSync<T>(Stopwatch sw)
{
HttpClient httpClient = new HttpClient();
var response = httpClient.GetAsync(_url).Result;
var obj = JsonConvert.DeserializeObject<T>(
response.Content.ReadAsStringAsync().Result);
sw.Stop();
Trace.WriteLine("HttpClient Sync " + sw.ElapsedMilliseconds);
}
public static void GetDataFromHttpClientAsync<T>(Stopwatch sw)
{
HttpClient httpClient = new HttpClient();
var response = httpClient.GetAsync(_url).ContinueWith(
(a) => {
JsonConvert.DeserializeObject<T>(
a.Result.Content.ReadAsStringAsync().Result);
sw.Stop();
Trace.WriteLine("HttpClient Async " + sw.ElapsedMilliseconds);
}, TaskContinuationOptions.None);
}
}
}
My Questions
- The REST calls return in 3-4s which is acceptable. Calls to REST service are initiated in controller methods which gets invoked from ajax calls. To begin with, the calls run in a different thread and doesn't block UI. So, can I just stick with sync calls?
- The above code was run in my localbox. In prod setup, DNS and proxy
lookup will be involved. Is there any advantage of using
HttpClient
overWebClient
? - Is
HttpClient
concurrency better thanWebClient
? From the test results, I seeWebClient
sync calls perform better. - Will
HttpClient
be a better design choice if we upgrade to .Net 4.5? Performance is the key design factor.
I live in both the F# and Web API worlds.
There's a lot of good stuff happening with Web API, especially in the form of message handlers for security, etc.
I know mine is only one opinion, but I would only recommend use of HttpClient
for any future work. Perhaps there's some way to leverage some of the other pieces coming out of System.Net.Http
without using that assembly directly, but I cannot imagine how that would work at this time.
Speaking of comparing these two
- HttpClient is more closer to HTTP than WebClient.
- HttpClient was not meant to be a complete replacement of Web Client, since there are things like report progress, custom URI scheme and making FTP calls that WebClient provides — but HttpClient doesn’t.
If you’re using .NET 4.5, please do use the async goodness with HttpClient that Microsoft provides to the developers. HttpClient is very symmetrical to the server side brethren of the HTTP those are HttpRequest and HttpResponse.
Update: 5 Reasons to use new HttpClient API
Strongly typed headers. Shared Caches, cookies and credentials Access to cookies and shared cookies Control over caching and shared cache. Inject your code module into the ASP.NET pipeline. Cleaner and modular code.
Reference
C# 5.0 Joseph Albahari
(Channel9 — Video Build 2013)
Five Great Reasons to Use the New HttpClient API to Connect to Web Services
这篇关于需要帮助的HttpClient的和WebClient的决定的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!