From http://aspnetmonsters.com/2016/08/2016-08-27-httpclientwrong/
You're correct. It's not thread-safe and can lead to deadlocks when used in high-load environments. The solution I ended up creating a special kind of pool for HttpClient objects: http://pastebin.com/jftEbWrc You just provide your HttpClient factory and dispose methods and the LimitedPool does the rest:
_httpClientPool = new LimitedPool( CreateHttpClient, client => client.Dispose(), HttpClientLifetime);
using (var httpClientContainer = _httpClientPool.Get()) { ... use httpClientContainer.Value ... }
When httpClientContainer is disposed, the HttpClient is actually returned back to the pool for other threads to use. When lifetime is reached next dispose will eventually call the Dispose method.