HttpContent:已添加具有相同键的项目

时间:2017-03-27 22:58:45

标签: c# race-condition httpcontent

我们在代码库中看到了以下堆栈跟踪:

System.ArgumentException: An item with the same key has already been added. 
   at System.Collections.Generic.Dictionary`2.Insert(TKey key, TValue value, Boolean add) 
   at System.Net.Http.Headers.HttpHeaders.AddHeaderToStore(String name, HeaderStoreItemInfo info) 
   at System.Net.Http.Headers.HttpHeaders.SetParsedValue(String name, Object value) 
   at System.Net.Http.Headers.HttpContentHeaders.get_ContentLength() 
   at System.Net.Http.HttpClientHandler.PrepareAndStartContentUpload(RequestState state) 

并将其缩小到我们调用

的代码中的某个位置
HttpContent.ReadAsStringAsync()

当发生这种情况时,我们确信多个线程正在使用HttpContent的实例,所有这些线程都试图读取实际内容。尚未弄清楚内容的阅读如何影响标题。

如果可以执行HttpContent的深度克隆,假设所有内容有效负载都已下载,我们就会调查此选项。

任何人遇到这种情况,如果是这样,你是如何解决的?

提前致谢。

1 个答案:

答案 0 :(得分:0)

对我来说,堆栈跟踪与响应的读取相关联是没有意义的。似乎更有可能在您发出请求之前,您有线程正在努力添加标头。也许与异步调试有些混淆? 当我有这样一行(客户端是HttpClient)

时,我已经看到了这一点

client.DefaultRequestHeaders.AcceptEncoding.Add(new System.Net.Http.Headers.StringWithQualityHeaderValue("gzip"));

在每个线程可以执行此操作的代码上,然后它变成了竞争条件,因为我相信httpclient会在它添加之前检查存在,然后如果在那个时间两个线程尝试添加它,它将像这样崩溃。根据您的设置,您可能需要将这样的内容移动到初始化中或围绕它进行锁定。