C#如何使用共享的HttpClient传递cookie [英] C# How to pass on a cookie using a shared HttpClient

查看:693
本文介绍了C#如何使用共享的HttpClient传递cookie的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我进行了以下设置:

JS客户端-> Web Api-> Web Api

JS client -> Web Api -> Web Api

我需要一直发送身份验证cookie。我的问题是将它从一个Web API发送到另一个。由于与使用FormsAuthentication的较旧系统集成,因此我必须传递auth cookie。

I need to send the auth cookie all the way down. My problem is sending it from one web api to another. Because of integration with an older system, that uses FormsAuthentication, I have to pass on the auth cookie.

出于性能原因,我共享HttpClients列表(每个网站一个) api)在以下字典中:

For performance reasons I share a list of HttpClients (one for each web api) in the following dictionary:

private static ConcurrentDictionary<ApiIdentifier, HttpClient> _clients = new ConcurrentDictionary<ApiIdentifier, HttpClient>();

因此,只要有一个标识符,我就可以获取相应的HttpClient。

So given an identifier I can grab the corresponding HttpClient.

以下方法有效,但是我很确定这是错误的代码:

The following works, but I'm pretty sure this is bad code:

HttpClient client = _clients[identifier];
var callerRequest = HttpContext.Current.Items["MS_HttpRequestMessage"] as HttpRequestMessage;
string authCookieValue = GetAuthCookieValue(callerRequest);

if (authCookieValue != null)
{
    client.DefaultRequestHeaders.Remove("Cookie");
    client.DefaultRequestHeaders.Add("Cookie", ".ASPXAUTH=" + authCookieValue);
}

HttpResponseMessage response = await client.PutAsJsonAsync(methodName, dataToSend);

// Handle response...

这是什么问题1)在请求中操纵 DefaultRequestHeaders 似乎是错误的,并且2)在共享HttpClient的情况下,两个同步请求可能会弄乱cookie。

Whats wrong about this is that 1) it seems wrong to manipulate DefaultRequestHeaders in a request and 2) potentially two simultanious requests may mess up the cookies, as the HttpClient is shared.

我一直在寻找解决方案,因为大多数匹配问题都会为每个请求实例化HttpClient,因此能够设置所需的标头,我试图避免

I've been searching for a while without finding a solution, as most having a matching problem instantiates the HttpClient for every request, hence being able to set the required headers, which I'm trying to avoid.

有一次,我收到了使用 HttpResponseMessage 处理的请求。

At one point I had get requests working using a HttpResponseMessage. Perhaps that can be of inspiration to a solution.

所以我的问题是:有没有一种方法可以使用HttpClient为单个请求设置Cookie,其他客户端使用同一实例?

So my question is: is there a way to set cookies for a single request using a HttpClient, that will be safe from other clients using the same instance?

推荐答案

除了调用PutAsJsonAsync()之外,您还可以使用HttpRequestMessage和SendAsync():

Instead of calling PutAsJsonAsync() you can use HttpRequestMessage and SendAsync():

Uri requestUri = ...;
HttpMethod method = HttpMethod.Get /*Put, Post, Delete, etc.*/;
var request = new HttpRequestMessage(method, requestUri);
request.Headers.TryAddWithoutValidation("Cookie", ".ASPXAUTH=" + authCookieValue);
request.Content = new StringContent(jsonDataToSend, Encoding.UTF8, "application/json");
var response = await client.SendAsync(request);

更新:
要确保您的HTTP客户端不存储响应中的任何cookie您需要执行以下操作:

UPDATE: To make sure that your HTTP client does not store any cookies from a response you need to do this:

var httpClient = new HttpClient(new HttpClientHandler() { UseCookies = false; });

否则,使用一个客户端并共享其他cookie可能会导致意外行为。

Otherwise you might get unexpected behavior by using one client and sharing other cookies.

这篇关于C#如何使用共享的HttpClient传递cookie的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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