HttpClientFactory がプライマリ ハンドラーとして SocketsHttpHandler を使用する
HttpClientFactory
では、名前付きオブジェクトと型指定されたHttpClient オブジェクトのHttpMessageHandler パイプラインを構成できます。 最も内側のハンドラー、または実際にネットワーク上で要求を送信するハンドラーは、 primary ハンドラーと呼ばれます。 構成されていない場合、このハンドラーは以前は常に HttpClientHandlerでした。 既定のプライマリ ハンドラーは実装の詳細ですが、それに依存するユーザーがいました。 たとえば、プライマリ ハンドラーを HttpClientHandler
にキャストして、 ClientCertificates、 UseCookies、 UseProxyなどのプロパティを設定するユーザーもいます。
この変更により、既定のプライマリ ハンドラーは、それをサポートするプラットフォーム上の SocketsHttpHandler です。 他のプラットフォーム (.NET Framework など) では、 HttpClientHandler は引き続き使用されます。
SocketsHttpHandler
には、HandlerLifetime値に一致するPooledConnectionLifetime プロパティ プリセットも追加されました。 ( HandlerLifetime
がユーザーによって構成された場合は、最新の値が反映されます)。
導入されたバージョン
.NET 9 Preview 6
以前の動作
既定のプライマリ ハンドラーは HttpClientHandler
されました。 プロパティを更新するために HttpClientHandler
にキャストすると、問題が発生しました。
services.AddHttpClient("test")
.ConfigurePrimaryHttpMessageHandler((h, _) =>
{
((HttpClientHandler)h).UseCookies = false;
});
// This worked.
var client = httpClientFactory.CreateClient("test");
新しい動作
SocketsHttpHandler
がサポートされているプラットフォームでは、PooledConnectionLifetime
がHandlerLifetime
値に設定された既定のプライマリ ハンドラーがSocketsHttpHandler
されるようになりました。 プロパティを更新するために HttpClientHandler
にキャストすると、 InvalidCastExceptionがスローされます。
たとえば、 Previous 動作 セクションと同じコードが InvalidCastExceptionをスローするようになりました。
System.InvalidCastException: 'System.Net.Http.SocketsHttpHandler' 型のオブジェクトを 'System.Net.Http.HttpClientHandler' 型にキャストできません。
破壊的変更の種類
この変更は、動作変更です。
変更理由
ユーザーが実行 HttpClientFactory
最も一般的な問題の 1 つは、 Named
または Typed
クライアントがシングルトン サービスで誤ってキャプチャされたとき、または一般に、指定された HandlerLifetimeよりも長い期間、どこかに保存される場合です。 このようなハンドラー HttpClientFactory
ローテーションできないため、DNS の変更を考慮しない可能性があります。
この問題は、PooledConnectionLifetimeを制御するオプションがある SocketsHttpHandler を使用して軽減できます。 HandlerLifetimeと同様に、プールされた接続の有効期間では、DNS の変更を取得するために接続を定期的に再作成できますが、レベルは低くなります。 PooledConnectionLifetime
設定されたクライアントは、シングルトンとして安全に使用できます。
残念ながら、シングルトンに Typed
クライアントを挿入するのは、残念ながら簡単で一見「直感的」です。 しかし、どのような種類のチェックやアナライザーを使用して、 HttpClient
がキャプチャされるはずでなかったときにキャプチャされていないことを確認するのは困難です。 また、結果の問題のトラブルシューティングも困難です。 そのため、誤った使用パターンの潜在的な影響を最小限に抑えるための予防措置として、 SocketsHttpHandler
軽減策が既定で適用されるようになりました。
この変更は、クライアントが (たとえば、ConfigurePrimaryHttpMessageHandler<THandler>(IHttpClientBuilder)を使用して) カスタム PrimaryHandlerを使用するようにエンド ユーザーによって構成されていない場合にのみ影響します。
推奨される操作
破壊的変更を回避するには、次の 3 つのオプションがあります。
各クライアントのプライマリ ハンドラーを明示的に指定して構成します。
services.AddHttpClient("test") .ConfigurePrimaryHttpMessageHandler(() => new HttpClientHandler() { UseCookies = false });
ConfigureHttpClientDefaults(IServiceCollection, Action<IHttpClientBuilder>)を使用して、すべてのクライアントの既定のプライマリ ハンドラーを上書きします。
services.ConfigureHttpClientDefaults(b => b.ConfigurePrimaryHttpMessageHandler(() => new HttpClientHandler() { UseCookies = false }));
構成アクションで、
HttpClientHandler
とSocketsHttpHandler
の両方を確認します。services.AddHttpClient("test") .ConfigurePrimaryHttpMessageHandler((h, _) => { if (h is HttpClientHandler hch) { hch.UseCookies = false; } if (h is SocketsHttpHandler shh) { shh.UseCookies = false; } });
影響を受ける API
.NET