这是从@Roman 修改的另一个版本,作为一种扩展方法,Linq 少一些,但不使用 StartsWith 更准确,如果 2 个或更多 cookie 以相同名称作为前缀,可能会导致误导性结果
public static string GetCookieValue(this HttpRequestHeaders requestHeaders, string cookieName)
{
foreach (var header in requestHeaders)
{
if (header.Key.Equals("Cookie", StringComparison.InvariantCultureIgnoreCase) == false)
continue;
var cookiesHeaderValue = header.Value.FirstOrDefault();
if (cookiesHeaderValue == null)
return null;
var cookieCollection = cookiesHeaderValue.Split(new[] { ';' }, StringSplitOptions.RemoveEmptyEntries);
foreach (var cookieNameValue in cookieCollection)
{
var parts = cookieNameValue.Split(new[] { '=' }, StringSplitOptions.RemoveEmptyEntries);
if (parts.Length != 2) continue;
if (parts[0].Trim().Equals(cookieName, StringComparison.InvariantCultureIgnoreCase))
return parts[1].Trim();
}
}
return null;
}
一些单元测试(nunit):
[TestCase("hello=world;cookies=are fun;", "hello", "world", true)]
[TestCase("HELlo=world;cookies=are fun", "hello", "world", true)]
[TestCase("HELlo= world;cookies=are fun", "hello", "world", true)]
[TestCase("HELlo =world;cookies=are fun", "hello", "world", true)]
[TestCase("hello = world;cookies=are fun;", "hello", "world", true)]
[TestCase("hellos=world;cookies=are fun", "hello", "world", false)]
[TestCase("hello=world;cookies?=are fun?", "hello", "world", true)]
[TestCase("hel?lo=world;cookies=are fun?", "hel?lo", "world", true)]
public void Get_Cookie_Value_From_HttpRequestHeaders(string cookieHeaderVal, string cookieName, string cookieVal, bool matches)
{
var request = new HttpRequestMessage(HttpMethod.Get, "http://test.com");
var requestHeaders = request.Headers;
requestHeaders.Add("Cookie", cookieHeaderVal);
var valueFromHeader = requestHeaders.GetCookieValue(cookieName);
if (matches)
{
Assert.IsNotNull(valueFromHeader);
Assert.AreEqual(cookieVal, valueFromHeader);
}
else
{
Assert.IsNull(valueFromHeader);
}
}