首页 > 解决方案 > 如果我想每次都更改 Referer 标头,就不能使用 GetStringAsync() 吗?

问题描述

似乎这HttpClient是进行 HTTP 通信的推荐方式。下载 URL 的 HTML 看起来很简单

var html = httpClient.GetStringAsync(url);

但我需要像Referer每次一样更改一些标题值。起初,我尝试

httpClient.DefaultRequestHeaders.Add("Referer", referrer);

,但这在第二次引起了错误。好像一经定下,就无法更改。

我搜索了一个解决方案并找到了一个(https://stackoverflow.com/a/12023307/455796),但这似乎比GetStringAsync. 我需要创建一个HttpRequestMessage,调用SendAsync,继续调用response.Content.ReadAsAsync,调用Wait(),然后读取结果。此外,评论说我需要处理HttpRequestMessage. 如果这是更改标题的唯一方法,我会这样做,但这是最好的方法吗?我不能使用GetStringAsync和更改标题值吗?

标签: c#httpclient

解决方案


你可以这样做:

using(var msg = new HttpRequestMessage(HttpMethod.Get, new Uri("https://www.test.com")))
{
    msg.Headers.Referrer = new Uri("https://www.example.com");
    using (var req = await _httpClient.SendAsync(msg))
    {
        var str1 = await req.Content.ReadAsStringAsync();
    }
}

或者,如果您想覆盖默认请求标头,请这样做:

_httpClient.DefaultRequestHeaders.Referrer = new Uri("https://www.example.com");
var str2 = await _httpClient.GetStringAsync("https://www.test.com/");

第一种方法是如果您想HttpClient在应用程序的整个生命周期中重用您的。这意味着,如果您与需要发出 HTTP 请求的每个对象或方法共享它。如果多个线程在每个线程修改标头时同时尝试使用它,这样做不会导致冲突。DeafaultRequestHeaders不是线程安全的......因此,如果多个线程同时修改DeafaultRequestHeaders属性,您可能会引发异常。


推荐阅读