如何在集成测试中添加AntiForgeryToken或__RequestVerificationToken
解决方案
不需要反序列化整个响应(除非Token在响应体JSON里),可以直接从HttpResponseMessage中提取__RequestVerificationToken,分两种常见场景处理:
1. 从响应Cookie中提取Token(ASP.NET Core常见场景)
大部分情况下,这个Token会通过响应的Cookie返回,直接从响应头的Cookie集合提取:
// 发送GET请求后,从响应头提取Token var getResponse = await httpClient.GetAsync(uri); var token = getResponse.Headers.GetValues("Set-Cookie") .FirstOrDefault(c => c.StartsWith("__RequestVerificationToken="))? .Split('=')[1] .Split(';')[0];
把Token加入POST请求的JSON
给你的AuthenticationRequest类新增对应属性:
public class AuthenticationRequest { public string Email { get; set; } public string Password { get; set; } public string ServiceType { get; set; } public string __RequestVerificationToken { get; set; } // 新增Token属性 }
然后赋值后再序列化:
authenticationRequest.__RequestVerificationToken = token; // 后续正常序列化对象为JSON即可 string jsonString = JsonConvert.SerializeObject( authenticationRequest, Formatting.Indented, new JsonSerializerSettings { ContractResolver = new CamelCasePropertyNamesContractResolver() });
2. 从响应体JSON中提取Token
如果Token是在GET响应的JSON体里,用JObject解析响应体直接提取(无需反序列化成完整类):
var getResponse = await httpClient.GetAsync(uri); var responseContent = await getResponse.Content.ReadAsStringAsync(); var token = JObject.Parse(responseContent)["__RequestVerificationToken"]?.ToString();
后续同样把Token赋值给AuthenticationRequest再序列化即可。
额外优化:改用Async/Await(避免死锁)
你的代码里用了.Result,建议改成异步测试方法,NUnit支持async Task类型的测试:
[Test] public async Task DoLogin() // 改成async Task { string uri = "/account/login"; AuthenticationRequest authenticationRequest = new AuthenticationRequest { Email = email, Password = password, ServiceType= ServiceType }; HttpClient httpClient = new HttpClient { BaseAddress = new Uri(Consts.APIBaseURL) }; httpClient.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json")); // 用await替代.Result var getResponse = await httpClient.GetAsync(uri); Console.WriteLine(getResponse.ToString()); // 提取Token(二选一) // 场景1:从Cookie提取 var token = getResponse.Headers.GetValues("Set-Cookie") .FirstOrDefault(c => c.StartsWith("__RequestVerificationToken="))? .Split('=')[1] .Split(';')[0]; // 场景2:从响应体JSON提取 // var responseContent = await getResponse.Content.ReadAsStringAsync(); // var token = JObject.Parse(responseContent)["__RequestVerificationToken"]?.ToString(); // 赋值Token authenticationRequest.__RequestVerificationToken = token; string jsonString = JsonConvert.SerializeObject( authenticationRequest, Formatting.Indented, new JsonSerializerSettings { ContractResolver = new CamelCasePropertyNamesContractResolver() }); HttpRequestMessage httpRequest = new HttpRequestMessage { RequestUri = new Uri(uri, UriKind.Relative), Method = HttpMethod.Post, Content = new StringContent(jsonString, Encoding.UTF8, "application/json") }; // 用await发送POST请求 var postResponse = await httpClient.SendAsync(httpRequest); Console.WriteLine(postResponse); var contentData = await postResponse.Content.ReadAsStringAsync(); Console.WriteLine("Content Data: \n" + contentData); }
内容的提问来源于stack exchange,提问作者Rahul Arya
相关产品推荐
相关产品推荐

