ASP.NET Core での HTTP.sys Web サーバーの実装
Note
これは、この記事の最新バージョンではありません。 現在のリリースについては、この記事の .NET 8 バージョンを参照してください。
警告
このバージョンの ASP.NET Core はサポート対象から除外されました。 詳細については、「.NET および .NET Core サポート ポリシー」を参照してください。 現在のリリースについては、この記事の .NET 8 バージョンを参照してください。
重要
この情報はリリース前の製品に関する事項であり、正式版がリリースされるまでに大幅に変更される可能性があります。 Microsoft はここに示されている情報について、明示か黙示かを問わず、一切保証しません。
現在のリリースについては、この記事の .NET 8 バージョンを参照してください。
作成者: Tom Dykstra、Chris Ross
HTTP.sys は、Windows 上でのみ動作する ASP.NET Core 用 Web サーバーです。 HTTP.sys は Kestrel サーバーの代替製品であり、Kestrel では提供されていない機能がいくつか用意されています。
重要
HTTP.sys は ASP.NET Core モジュールと互換性がなく、IIS や IIS Express で使用することはできません。
HTTP.sys は、次の機能をサポートします。
- Windows 認証
- ポート共有
- SNI を使用する HTTPS
- HTTP/2 over TLS (Windows 10 以降)
- 直接ファイル伝送
- 応答キャッシュ
- WebSocket (Windows 8 以降)
サポートされている Windows バージョン:
- Windows 7 以降
- Windows Server 2008 R2 以降
サンプル コードを表示またはダウンロードします (ダウンロード方法)。
HTTP.sys を使用するタイミング
HTTP.sys は、次のような展開に適しています。
IIS を使用せず、インターネットに直接サーバーを公開する必要がある。
内部の展開から Kestrel では使用できない機能が要求されている。 詳細については、Kestrel と HTTP.sys の比較に関するページを参照してください。
HTTP.sys は、さまざまな種類の攻撃を防ぎ、フル機能の Web サーバーとして堅牢性、セキュリティ、スケーラビリティを提供する、成熟したテクノロジです。 IIS 自体が、HTTP.sys 上で HTTP リスナーとして実行されています。
HTTP/2 のサポート
HTTP/2 は、次の基本要件が満たされている場合に、ASP.NET Core アプリに対して有効になります。
- Windows Server 2016/Windows 10 以降
- アプリケーション レイヤー プロトコル ネゴシエーション (ALPN) 接続
- TLS 1.2 以降の接続
Http/2 接続が確立されると、HttpRequest.Protocol が HTTP/2
を報告します。
HTTP/2 は既定で有効になっています。 Http/2 接続が確立されない場合、接続は http/1.1 にフォールバックします。 Windows の今後のリリースで、HTTP.sys で HTTP/2 を無効にする機能を含む HTTP/2 構成フラグが使用可能になる予定です。
HTTP/3 のサポート
HTTP/3 は、次の基本要件が満たされている場合に、ASP.NET Core アプリに対して有効になります。
- Windows Server 2022/Windows 11 以降。
https
URL バインドが使用されている。- EnableHttp3 レジストリ キーが設定されている。
以前のバージョンの Windows 11 ビルドでは、Windows Insider ビルドの使用が必要になる場合があります。
HTTP/3 は、alt-svc
ヘッダーを介して HTTP/1.1 または HTTP/2 からのアップグレードとして検出されます。 これは、最初の要求では HTTP/3 に切り替える前に、通常 HTTP/1.1 または HTTP/2 が使用されることを意味します。 Http.Sys によって alt-svc
ヘッダーは自動的に追加されないため、アプリケーションで追加する必要があります。 次のコードは、alt-svc
応答ヘッダーを追加するミドルウェアの例を示しています。
app.Use((context, next) =>
{
context.Response.Headers.AltSvc = "h3=\":443\"";
return next(context);
});
上記のコードを要求パイプラインの早い段階に配置します。
Http.Sys では、HTTP/3 が使用可能であることをクライアントに通知するために、応答ヘッダーではなく AltSvc HTTP/2 プロトコル メッセージの送信もサポートされています。 EnableAltSvc レジストリ キーに関するページを参照してください。 これには、IP アドレスではなくホスト名を使用する netsh sslcert バインドが必要です。
Kerberos を使用したカーネル モード認証
HTTP.sys では、Kerberos 認証プロトコルを使用したカーネル モード認証に処理が委任されます。 Kerberos および HTTP.sys ではユーザー モード認証がサポートされていません。 Active Directory から取得され、クライアントによって、ユーザーを認証するサーバーに転送される Kerberos トークン/チケットを暗号化解除するには、コンピューター アカウントを使用する必要があります。 アプリのユーザーではなく、ホストのサービス プリンシパル名 (SPN) を登録します。
カーネル モード応答バッファリングのサポート
一部のシナリオでは、待機時間の長い少量の書き込みが大量に発生すると、HTTP.sys
のパフォーマンスに大きな影響を与える場合があります。 この影響は、HTTP.sys
に Pipe バッファーが実装されていないことが原因です。 これらのシナリオでパフォーマンスを向上させるため、HTTP.sys
では応答バッファリングがサポートされています。 HttpSysOptions.EnableKernelResponseBuffering を true
に設定して、バッファリングを有効にします。
応答バッファリングは、同期 I/O を実行するアプリで、または非同期 I/O で未処理の書き込みを一度に 1 つしか実行しないアプリで有効にする必要があります。 これらのシナリオでは、応答バッファリングにより、待機時間の長い接続に対してスループットが大幅に向上する場合があります。
非同期 I/O を使用し、未処理の書き込みを一度に複数実行する場合があるアプリでは、このフラグを使用しないでください。 このフラグを有効にすると、HTTP.Sys により CPU とメモリの使用率が高くなる場合があります。
HTTP.sys の使用方法
HTTP.sys を使用するように ASP.NET Core アプリを構成する
ホストを構築するときに UseHttpSys 拡張メソッドを呼び出し、必要な HttpSysOptions を指定します。 次の例では、既定値にオプションを設定しています。
using Microsoft.AspNetCore.Hosting.Server;
using Microsoft.AspNetCore.Hosting.Server.Features;
using Microsoft.AspNetCore.Http.Features;
using Microsoft.AspNetCore.Server.HttpSys;
var builder = WebApplication.CreateBuilder(args);
builder.WebHost.UseHttpSys(options =>
{
options.AllowSynchronousIO = false;
options.Authentication.Schemes = AuthenticationSchemes.None;
options.Authentication.AllowAnonymous = true;
options.MaxConnections = null;
options.MaxRequestBodySize = 30_000_000;
options.UrlPrefixes.Add("http://localhost:5005");
});
builder.Services.AddRazorPages();
var app = builder.Build();
HTTP.sys の追加の構成は、レジストリ設定を通じて処理されます。
HTTP.sys オプションの詳細については、「HttpSysOptions」を参照してください。
MaxRequestBodySize
要求本文の最大許容サイズ (バイト単位) です。 null
に設定する場合、要求本文の最大サイズは制限されません。 この制限は、アップグレード済みの接続 (常に無制限) には影響しません。
1 つの IActionResult
に対する ASP.NET Core MVC アプリの制限をオーバーライドする方法として、アクション メソッドに対して RequestSizeLimitAttribute 属性を使用することをお勧めします。
[RequestSizeLimit(100000000)]
public IActionResult MyActionMethod()
アプリが要求の読み取りを開始した後に、アプリが要求に対する制限を構成しようとすると、例外がスローされます。 IsReadOnly
プロパティを使用して、MaxRequestBodySize
プロパティが読み取り専用状態にあるかどうか、つまり制限を構成するには遅すぎるかどうかを示すことができます。
要求ごとにアプリで MaxRequestBodySize をオーバーライドする必要がある場合は、IHttpMaxRequestBodySizeFeature を使います。
app.Use((context, next) =>
{
context.Features.GetRequiredFeature<IHttpMaxRequestBodySizeFeature>()
.MaxRequestBodySize = 10 * 1024;
var server = context.RequestServices
.GetRequiredService<IServer>();
var serverAddressesFeature = server.Features
.GetRequiredFeature<IServerAddressesFeature>();
var addresses = string.Join(", ", serverAddressesFeature.Addresses);
var loggerFactory = context.RequestServices
.GetRequiredService<ILoggerFactory>();
var logger = loggerFactory.CreateLogger("Sample");
logger.LogInformation("Addresses: {addresses}", addresses);
return next(context);
});
Visual Studio を使用する場合は、アプリが IIS または IIS Express を実行するように構成されていないことを確認します。
Visual Studio では、既定の起動プロファイルは IIS Express 用です。 プロジェクトをコンソール アプリとして実行するには、次のスクリーンショットに示すように、選択したプロファイルを手動で変更します。
Windows Server を構成する
アプリに対して開くポートを決めたら、Windows ファイアウォールか New-NetFirewallRule PowerShell コマンドレットを使用して、トラフィックが HTTP.sys に到達できるようにファイアウォールのポートを開きます。 次のコマンドとアプリの構成では、ポート 443 を使用します。
Azure VM に展開する場合は、ネットワーク セキュリティ グループ内でポートを開きます。 次のコマンドとアプリの構成では、ポート 443 を使用します。
必要に応じて、X.509 証明書を取得してインストールします。
Windows の場合は、New-SelfSignedCertificate PowerShell コマンドレットを使用して自己署名証明書を作成します。 サポート対象外の例については、UpdateIISExpressSSLForChrome.ps1 を参照してください。
自己署名証明書か CA 署名証明書のいずれかをサーバーの Local Machine>Personal ストアにインストールします。
アプリがフレームワークに依存する展開である場合は、.NET Core、.NET Framework、またはその両方 (アプリが .NET Framework をターゲットとする .NET Core アプリである場合) をインストールします。
- .NET Core: アプリで .NET Core が必要な場合は、.NET Core のダウンロードから .NET Core Runtime インストーラーを取得して実行します。 サーバーに SDK 全体をインストールしないでください。
- .NET Framework:アプリで .NET Framework が必要な場合は、.NET Framework のインストール ガイドを参照してください。 必要な .NET Framework をインストールします。 最新の .NET Framework のインストーラーは .NET Core のダウンロード ページから入手できます。
アプリが自己完結型の展開の場合、アプリの展開内にランタイムが含まれています。 サーバーにフレームワークをインストールする必要はありません。
アプリに URL とポートを構成します。
既定では、ASP.NET Core は
http://localhost:5000
にバインドされます。 URL プレフィックスとポートを構成するには、次のオプションがあります。- UseUrls
urls
コマンド ライン引数ASPNETCORE_URLS
環境変数- UrlPrefixes
次のコード例は、サーバーのローカル IP アドレス
10.0.0.4
を使ってポート 443 上で UrlPrefixes を使う方法を示しています。var builder = WebApplication.CreateBuilder(args); builder.WebHost.UseHttpSys(options => { options.UrlPrefixes.Add("https://10.0.0.4:443"); }); builder.Services.AddRazorPages(); var app = builder.Build();
UrlPrefixes
の利点は、プレフィックスの形式が正しくなかった場合、すぐにエラー メッセージが生成されることです。UrlPrefixes
の設定はUseUrls
/urls
/ASPNETCORE_URLS
の設定をオーバーライドします。 したがって、UseUrls
、urls
、およびASPNETCORE_URLS
環境変数の利点は、Kestrel と HTTP.sys を簡単に切り替えられることです。HTTP.sys は、URL プレフィックスで次の 2 種類のワイルドカードを認識します:
*
は弱いバインディング であり、フォールバック バインディングとも呼ばれます。 URL プレフィックスがhttp://*:5000
で、他の何かがポート 5000 にバインドされている場合、このバインディングは使用されません。+
は強力なバインディングです。 URL プレフィックスがhttp://+:5000
の場合、このバインディングは他のポート 5000 バインドの前に使用されます。
詳細については、「UrlPrefix 文字列」を参照してください。
警告
最上位のワイルドカードのバインド (
http://*:80/
とhttp://+:80
) は使用しては いけません 。 最上位のワイルドカードのバインドを使用すると、アプリにセキュリティの脆弱性が生じます。 これは、強力と脆弱の両方のワイルドカードに適用されます。 ワイルドカードではなく、明示的なホスト名か IP アドレスを使用してください。 親ドメイン全体を制御する場合、サブドメインのワイルドカードのバインド (たとえば、*.mysub.com
) がセキュリティ リスクになることはありません (脆弱である*.com
とは対照的)。 詳細については、RFC 9110: セクション 7.2: 「Host and :authority (ホストと :authority)」を参照してください。多くの場合、アプリとコンテナーには、リッスンするためのポート (ポート 80 など) のみが与えられます。ホストやパスなどの追加の制約は課せられません。 HTTP_PORTS と HTTPS_PORTS は、Kestrel および HTTP.sys サーバー用にリッスン ポートを指定するための構成キーです。 これらのキーは、
DOTNET_
またはASPNETCORE_
プレフィックスで定義された環境変数として指定することも、appsettings.json
などの他の構成入力を介して直接指定することもできます。 それぞれは、次の例に示すように、ポート値をセミコロンで区切ってリストしたものです。ASPNETCORE_HTTP_PORTS=80;8080 ASPNETCORE_HTTPS_PORTS=443;8081
前述の例は、次の構成の省略形であり、スキーム (HTTP または HTTPS) と任意のホストまたは IP が指定されています。
ASPNETCORE_URLS=http://*:80/;http://*:8080/;https://*:443/;https://*:8081/
HTTP_PORTS および HTTPS_PORTS 構成キーは優先度が低く、コードで直接指定された URL または値によってオーバーライドされます。 証明書は引き続き、HTTPS 用のサーバー固有のメカニズムを介して個別に構成する必要があります。
これらの構成キーは、最上位のワイルドカード バインドと同等です。 これらは開発およびコンテナーのシナリオには便利ですが、他のサービスもホストする可能性があるコンピューター上で実行する場合は、ワイルドカードを避けてください。
サーバーで URL プレフィックスを事前登録します。
HTTP.sys を構成するための組み込みツールは、netsh.exe です。 netsh.exe を使用して、URL プレフィックスを予約し、X.509 証明書を割り当てることができます。 ツールを使用するには管理者特権が必要です。
netsh.exe ツールを使用して、アプリ用に URL を登録します。
netsh http add urlacl url=<URL> user=<USER>
<URL>
:完全修飾 URL (Uniform Resource Locator)。 ワイルドカードのバインドは使用しないでください。 有効なホスト名かローカル IP アドレスを使用してください。 "URL の末尾にはスラッシュが必要です。 "<USER>
:ユーザーまたはユーザー グループの名前を指定します。
次の例では、サーバーのローカル IP アドレスは
10.0.0.4
です。netsh http add urlacl url=https://10.0.0.4:443/ user=Users
URL が登録されると、ツールから
URL reservation successfully added
という応答があります。登録済みの URL を削除するには、
delete urlacl
コマンドを使用します。netsh http delete urlacl url=<URL>
サーバーで X.509 証明書を登録します。
netsh.exe ツールを使用して、アプリ用の証明書を登録します。
netsh http add sslcert ipport=<IP>:<PORT> certhash=<THUMBPRINT> appid="{<GUID>}"
<IP>
:バインド用のローカル IP アドレスを指定します。 ワイルドカードのバインドは使用しないでください。 有効な IP アドレスを使用してください。<PORT>
:バインド用のポートを指定します。<THUMBPRINT>
:X.509 証明書の拇印です。<GUID>
:情報提供を目的として開発者によって生成された、アプリを表す GUID です。
参照用に、この GUID をパッケージ タグとしてアプリに格納します。
- Visual Studio での操作: [][]
- ソリューション エクスプローラー内でアプリを右クリックし、 [プロパティ] をクリックして、アプリのプロジェクト プロパティを開きます。
- [パッケージ] タブを選択します。
- 作成した GUID を [タグ] フィールドに入力します。
- Visual Studio を使用しない場合:
アプリのプロジェクト ファイルを開きます。
作成した GUID を指定した
<PackageTags>
プロパティを、新規または既存の<PropertyGroup>
に追加します。<PropertyGroup> <PackageTags>00001111-aaaa-2222-bbbb-3333cccc4444</PackageTags> </PropertyGroup>
次に例を示します。
- サーバーのローカル IP アドレスは
10.0.0.4
です。 - オンラインのランダム GUID ジェネレーターによって、
appid
の値が提供されます。
netsh http add sslcert ipport=10.0.0.4:443 certhash=b66ee04419d4ee37464ab8785ff02449980eae10 appid="{00001111-aaaa-2222-bbbb-3333cccc4444}"
証明書が登録されると、ツールから
SSL Certificate successfully added
という応答があります。証明書の登録を削除するには、
delete sslcert
コマンドを使用します。netsh http delete sslcert ipport=<IP>:<PORT>
以下は、netsh.exe のリファレンス ドキュメントです。
- Netsh Commands for Hypertext Transfer Protocol (HTTP) (ハイパーテキスト転送プロトコル (HTTP) 用の Netsh コマンド)
- UrlPrefix Strings (UrlPrefix 文字列)
アプリを実行します。
1024 より大きいポート番号で (HTTPS ではなく) HTTP を使用して localhost にバインドする場合、アプリの実行に管理者権限は必要ありません。 その他の構成の場合 (たとえば、ローカル IP アドレスを使用する場合やポート 443 にバインドする場合)、管理者権限でアプリを実行します。
サーバーのパブリック IP アドレスでアプリが応答します。 この例では、サーバーは自身のパブリック IP アドレス
104.214.79.47
でインターネットからアクセスされます。この例では開発証明書が使用されています。 証明書が信頼できないというブラウザーの警告がバイパスされた後に、ページが安全に読み込まれます。
プロキシ サーバーとロード バランサーのシナリオ
インターネットや企業ネットワークからの要求とやりとりする HTTP.sys でホストされるアプリの場合、プロキシ サーバーやロード バランサーの背後でホストするとき、追加の構成が必要になることがあります。 詳細については、「プロキシ サーバーとロード バランサーを使用するために ASP.NET Core を構成する」を参照してください。
IHttpSysRequestTimingFeature を使用して詳細なタイミング情報を取得する
IHttpSysRequestTimingFeature では、要求の詳細なタイミング情報が提供されます。
- タイムスタンプは、QueryPerformanceCounter を使用して取得されます。
- タイムスタンプの頻度は、QueryPerformanceFrequency を使用して取得できます。
- タイミングのインデックスを HttpSysRequestTimingType にキャストして、タイミングが何を表しているのかを把握できます。
- 現在の要求でタイミングを利用できない場合、値は 0 になることがあります。
- Windows 10 バージョン 2004、Windows Server 2022 以降が必要です。
using Microsoft.AspNetCore.Http.Features;
using Microsoft.AspNetCore.Server.HttpSys;
var builder = WebApplication.CreateBuilder(args);
builder.WebHost.UseHttpSys();
var app = builder.Build();
app.Use((context, next) =>
{
var feature = context.Features.GetRequiredFeature<IHttpSysRequestTimingFeature>();
var loggerFactory = context.RequestServices.GetRequiredService<ILoggerFactory>();
var logger = loggerFactory.CreateLogger("Sample");
var timestamps = feature.Timestamps;
for (var i = 0; i < timestamps.Length; i++)
{
var timestamp = timestamps[i];
var timingType = (HttpSysRequestTimingType)i;
logger.LogInformation("Timestamp {timingType}: {timestamp}",
timingType, timestamp);
}
return next(context);
});
app.MapGet("/", () => Results.Ok());
app.Run();
IHttpSysRequestTimingFeature.TryGetTimestamp では、指定されたタイミングの種類のタイムスタンプを取得します。
using Microsoft.AspNetCore.Http.Features;
using Microsoft.AspNetCore.Server.HttpSys;
var builder = WebApplication.CreateBuilder(args);
builder.WebHost.UseHttpSys();
var app = builder.Build();
app.Use((context, next) =>
{
var feature = context.Features.GetRequiredFeature<IHttpSysRequestTimingFeature>();
var loggerFactory = context.RequestServices.GetRequiredService<ILoggerFactory>();
var logger = loggerFactory.CreateLogger("Sample");
var timingType = HttpSysRequestTimingType.RequestRoutingEnd;
if (feature.TryGetTimestamp(timingType, out var timestamp))
{
logger.LogInformation("Timestamp {timingType}: {timestamp}",
timingType, timestamp);
}
else
{
logger.LogInformation("Timestamp {timingType}: not available for the "
+ "current request", timingType);
}
return next(context);
});
app.MapGet("/", () => Results.Ok());
app.Run();
IHttpSysRequestTimingFeature.TryGetElapsedTime は、指定された 2 つのタイミング間の経過時間を示します。
using Microsoft.AspNetCore.Http.Features;
using Microsoft.AspNetCore.Server.HttpSys;
var builder = WebApplication.CreateBuilder(args);
builder.WebHost.UseHttpSys();
var app = builder.Build();
app.Use((context, next) =>
{
var feature = context.Features.GetRequiredFeature<IHttpSysRequestTimingFeature>();
var loggerFactory = context.RequestServices.GetRequiredService<ILoggerFactory>();
var logger = loggerFactory.CreateLogger("Sample");
var startingTimingType = HttpSysRequestTimingType.RequestRoutingStart;
var endingTimingType = HttpSysRequestTimingType.RequestRoutingEnd;
if (feature.TryGetElapsedTime(startingTimingType, endingTimingType, out var elapsed))
{
logger.LogInformation(
"Elapsed time {startingTimingType} to {endingTimingType}: {elapsed}",
startingTimingType,
endingTimingType,
elapsed);
}
else
{
logger.LogInformation(
"Elapsed time {startingTimingType} to {endingTimingType}:"
+ " not available for the current request.",
startingTimingType,
endingTimingType);
}
return next(context);
});
app.MapGet("/", () => Results.Ok());
app.Run();
gRPC をサポートする高度な HTTP/2 機能
HTTP.sys 内の追加の HTTP/2 機能によって、gRPC がサポートされています。これには、応答トレーラーやリセット フレームの送信に関するサポートが含まれます。
HTTP.sys で gRPC を実行するための要件:
- Windows 11 ビルド 22000 またはそれ以降、Windows Server 2022 ビルド 20348 またはそれ以降が必要です。
- TLS 1.2 またはそれ以降の接続。
予告編
HTTP トレーラーは HTTP ヘッダーに似ていますが、応答本文の送信後に送信される点が異なります。 IIS と HTTP.sys の場合は、HTTP/2 応答トレーラーのみがサポートされています。
if (httpContext.Response.SupportsTrailers())
{
httpContext.Response.DeclareTrailer("trailername");
// Write body
httpContext.Response.WriteAsync("Hello world");
httpContext.Response.AppendTrailer("trailername", "TrailerValue");
}
上記のコード例では次のようになっています。
SupportsTrailers
によって、応答におけるトレーラーが確実にサポートされます。DeclareTrailer
によって、指定したトレーラー名がTrailer
応答ヘッダーに追加されます。 応答のトレーラーを宣言することは省略可能ですが、推奨されています。DeclareTrailer
を呼び出す場合、それは、応答ヘッダーを送信する前に行う必要があります。AppendTrailer
によって、トレーラーが追加されます。
Reset
リセットを使用すると、指定されたエラー コードを使用してサーバーに HTTP/2 要求をリセットさせることができます。 リセット要求は中止されたと見なされます。
var resetFeature = httpContext.Features.Get<IHttpResetFeature>();
resetFeature.Reset(errorCode: 2);
上記のコード例の Reset
により、INTERNAL_ERROR
エラー コードが指定されています。 HTTP/2 エラー コードの詳細については、HTTP/2 仕様の「エラーコード」セクションを参照してください。
トレース
HTTP.sys からトレースを取得する方法については、「HTTP.sys 管理のシナリオ」を参照してください。
その他のリソース
HTTP.sys は、Windows 上でのみ動作する ASP.NET Core 用 Web サーバーです。 HTTP.sys は Kestrel サーバーの代替製品であり、Kestrel では提供されていない機能がいくつか用意されています。
重要
HTTP.sys は ASP.NET Core モジュールと互換性がなく、IIS や IIS Express で使用することはできません。
HTTP.sys は、次の機能をサポートします。
- Windows 認証
- ポート共有
- SNI を使用する HTTPS
- HTTP/2 over TLS (Windows 10 以降)
- 直接ファイル伝送
- 応答キャッシュ
- WebSocket (Windows 8 以降)
サポートされている Windows バージョン:
- Windows 7 以降
- Windows Server 2008 R2 以降
サンプル コードを表示またはダウンロードします (ダウンロード方法)。
HTTP.sys を使用するタイミング
HTTP.sys は、次のような展開に適しています。
IIS を使用せず、インターネットに直接サーバーを公開する必要がある。
内部の展開から Kestrel では使用できない機能が要求されている。 詳細については、Kestrel と HTTP.sys の比較に関するページを参照してください。
HTTP.sys は、さまざまな種類の攻撃を防ぎ、フル機能の Web サーバーとして堅牢性、セキュリティ、スケーラビリティを提供する、成熟したテクノロジです。 IIS 自体が、HTTP.sys 上で HTTP リスナーとして実行されています。
HTTP/2 のサポート
HTTP/2 は、次の基本要件が満たされている場合に、ASP.NET Core アプリに対して有効になります。
- Windows Server 2016/Windows 10 以降
- アプリケーション レイヤー プロトコル ネゴシエーション (ALPN) 接続
- TLS 1.2 以降の接続
Http/2 接続が確立されると、HttpRequest.Protocol が HTTP/2
を報告します。
HTTP/2 は既定で有効になっています。 Http/2 接続が確立されない場合、接続は http/1.1 にフォールバックします。 Windows の今後のリリースで、HTTP.sys で HTTP/2 を無効にする機能を含む HTTP/2 構成フラグが使用可能になる予定です。
HTTP/3 のサポート
HTTP/3 は、次の基本要件が満たされている場合に、ASP.NET Core アプリに対して有効になります。
- Windows Server 2022/Windows 11 以降。
https
URL バインドが使用されている。- EnableHttp3 レジストリ キーが設定されている。
以前のバージョンの Windows 11 ビルドでは、Windows Insider ビルドの使用が必要になる場合があります。
HTTP/3 は、alt-svc
ヘッダーを介して HTTP/1.1 または HTTP/2 からのアップグレードとして検出されます。 これは、最初の要求では HTTP/3 に切り替える前に、通常 HTTP/1.1 または HTTP/2 が使用されることを意味します。 Http.Sys によって alt-svc
ヘッダーは自動的に追加されないため、アプリケーションで追加する必要があります。 次のコードは、alt-svc
応答ヘッダーを追加するミドルウェアの例を示しています。
app.Use((context, next) =>
{
context.Response.Headers.AltSvc = "h3=\":443\"";
return next(context);
});
上記のコードを要求パイプラインの早い段階に配置します。
Http.Sys では、HTTP/3 が使用可能であることをクライアントに通知するために、応答ヘッダーではなく AltSvc HTTP/2 プロトコル メッセージの送信もサポートされています。 EnableAltSvc レジストリ キーに関するページを参照してください。 これには、IP アドレスではなくホスト名を使用する netsh sslcert バインドが必要です。
Kerberos を使用したカーネル モード認証
HTTP.sys では、Kerberos 認証プロトコルを使用したカーネル モード認証に処理が委任されます。 Kerberos および HTTP.sys ではユーザー モード認証がサポートされていません。 Active Directory から取得され、クライアントによって、ユーザーを認証するサーバーに転送される Kerberos トークン/チケットを暗号化解除するには、コンピューター アカウントを使用する必要があります。 アプリのユーザーではなく、ホストのサービス プリンシパル名 (SPN) を登録します。
HTTP.sys の使用方法
HTTP.sys を使用するように ASP.NET Core アプリを構成する
ホストを構築するときに UseHttpSys 拡張メソッドを呼び出し、必要な HttpSysOptions を指定します。 次の例では、既定値にオプションを設定しています。
public static IHostBuilder CreateHostBuilder(string[] args) =>
Host.CreateDefaultBuilder(args)
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.UseHttpSys(options =>
{
options.AllowSynchronousIO = false;
options.Authentication.Schemes = AuthenticationSchemes.None;
options.Authentication.AllowAnonymous = true;
options.MaxConnections = null;
options.MaxRequestBodySize = 30000000;
options.UrlPrefixes.Add("http://localhost:5005");
});
webBuilder.UseStartup<Startup>();
});
HTTP.sys の追加の構成は、レジストリ設定を通じて処理されます。
HTTP.sys オプションの詳細については、「HttpSysOptions」を参照してください。
MaxRequestBodySize
要求本文の最大許容サイズ (バイト単位) です。 null
に設定する場合、要求本文の最大サイズは制限されません。 この制限は、アップグレード済みの接続 (常に無制限) には影響しません。
1 つの IActionResult
に対する ASP.NET Core MVC アプリの制限をオーバーライドする方法として、アクション メソッドに対して RequestSizeLimitAttribute 属性を使用することをお勧めします。
[RequestSizeLimit(100000000)]
public IActionResult MyActionMethod()
アプリが要求の読み取りを開始した後に、アプリが要求に対する制限を構成しようとすると、例外がスローされます。 IsReadOnly
プロパティを使用して、MaxRequestBodySize
プロパティが読み取り専用状態にあるかどうか、つまり制限を構成するには遅すぎるかどうかを示すことができます。
要求ごとにアプリで MaxRequestBodySize をオーバーライドする必要がある場合は、IHttpMaxRequestBodySizeFeature を使います。
public void Configure(IApplicationBuilder app, IWebHostEnvironment env,
ILogger<Startup> logger, IServer server)
{
app.Use(async (context, next) =>
{
context.Features.Get<IHttpMaxRequestBodySizeFeature>()
.MaxRequestBodySize = 10 * 1024;
var serverAddressesFeature =
app.ServerFeatures.Get<IServerAddressesFeature>();
var addresses = string.Join(", ", serverAddressesFeature?.Addresses);
logger.LogInformation("Addresses: {Addresses}", addresses);
await next.Invoke();
});
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
else
{
app.UseExceptionHandler("/Error");
}
app.UseStaticFiles();
app.UseRouting();
app.UseEndpoints(endpoints =>
{
endpoints.MapRazorPages();
});
}
Visual Studio を使用する場合は、アプリが IIS または IIS Express を実行するように構成されていないことを確認します。
Visual Studio では、既定の起動プロファイルは IIS Express 用です。 プロジェクトをコンソール アプリとして実行するには、次のスクリーンショットに示すように、選択したプロファイルを手動で変更します。
Windows Server を構成する
アプリに対して開くポートを決めたら、Windows ファイアウォールか New-NetFirewallRule PowerShell コマンドレットを使用して、トラフィックが HTTP.sys に到達できるようにファイアウォールのポートを開きます。 次のコマンドとアプリの構成では、ポート 443 を使用します。
Azure VM に展開する場合は、ネットワーク セキュリティ グループ内でポートを開きます。 次のコマンドとアプリの構成では、ポート 443 を使用します。
必要に応じて、X.509 証明書を取得してインストールします。
Windows の場合は、New-SelfSignedCertificate PowerShell コマンドレットを使用して自己署名証明書を作成します。 サポート対象外の例については、UpdateIISExpressSSLForChrome.ps1 を参照してください。
自己署名証明書か CA 署名証明書のいずれかをサーバーの Local Machine>Personal ストアにインストールします。
アプリがフレームワークに依存する展開である場合は、.NET Core、.NET Framework、またはその両方 (アプリが .NET Framework をターゲットとする .NET Core アプリである場合) をインストールします。
- .NET Core: アプリで .NET Core が必要な場合は、.NET Core のダウンロードから .NET Core Runtime インストーラーを取得して実行します。 サーバーに SDK 全体をインストールしないでください。
- .NET Framework:アプリで .NET Framework が必要な場合は、.NET Framework のインストール ガイドを参照してください。 必要な .NET Framework をインストールします。 最新の .NET Framework のインストーラーは .NET Core のダウンロード ページから入手できます。
アプリが自己完結型の展開の場合、アプリの展開内にランタイムが含まれています。 サーバーにフレームワークをインストールする必要はありません。
アプリに URL とポートを構成します。
既定では、ASP.NET Core は
http://localhost:5000
にバインドされます。 URL プレフィックスとポートを構成するには、次のオプションがあります。- UseUrls
urls
コマンド ライン引数ASPNETCORE_URLS
環境変数- UrlPrefixes
次のコード例は、サーバーのローカル IP アドレス
10.0.0.4
を使ってポート 443 上で UrlPrefixes を使う方法を示しています。public static IHostBuilder CreateHostBuilder(string[] args) => Host.CreateDefaultBuilder(args) .ConfigureWebHostDefaults(webBuilder => { webBuilder.UseHttpSys(options => { options.UrlPrefixes.Add("https://10.0.0.4:443"); }); webBuilder.UseStartup<Startup>(); });
UrlPrefixes
の利点は、プレフィックスの形式が正しくなかった場合、すぐにエラー メッセージが生成されることです。UrlPrefixes
の設定はUseUrls
/urls
/ASPNETCORE_URLS
の設定をオーバーライドします。 したがって、UseUrls
、urls
、およびASPNETCORE_URLS
環境変数の利点は、Kestrel と HTTP.sys を簡単に切り替えられることです。HTTP.sys では、HTTP サーバー API の UrlPrefix 文字列形式が使用されます。
警告
最上位のワイルドカードのバインド (
http://*:80/
とhttp://+:80
) は使用しては いけません 。 最上位のワイルドカードのバインドを使用すると、アプリにセキュリティの脆弱性が生じます。 これは、強力と脆弱の両方のワイルドカードに適用されます。 ワイルドカードではなく、明示的なホスト名か IP アドレスを使用してください。 親ドメイン全体を制御する場合、サブドメインのワイルドカードのバインド (たとえば、*.mysub.com
) がセキュリティ リスクになることはありません (脆弱である*.com
とは対照的)。 詳細については、RFC 9110: セクション 7.2: 「Host and :authority (ホストと :authority)」を参照してください。サーバーで URL プレフィックスを事前登録します。
HTTP.sys を構成するための組み込みツールは、netsh.exe です。 netsh.exe を使用して、URL プレフィックスを予約し、X.509 証明書を割り当てることができます。 ツールを使用するには管理者特権が必要です。
netsh.exe ツールを使用して、アプリ用に URL を登録します。
netsh http add urlacl url=<URL> user=<USER>
<URL>
:完全修飾 URL (Uniform Resource Locator)。 ワイルドカードのバインドは使用しないでください。 有効なホスト名かローカル IP アドレスを使用してください。 "URL の末尾にはスラッシュが必要です。 "<USER>
:ユーザーまたはユーザー グループの名前を指定します。
次の例では、サーバーのローカル IP アドレスは
10.0.0.4
です。netsh http add urlacl url=https://10.0.0.4:443/ user=Users
URL が登録されると、ツールから
URL reservation successfully added
という応答があります。登録済みの URL を削除するには、
delete urlacl
コマンドを使用します。netsh http delete urlacl url=<URL>
サーバーで X.509 証明書を登録します。
netsh.exe ツールを使用して、アプリ用の証明書を登録します。
netsh http add sslcert ipport=<IP>:<PORT> certhash=<THUMBPRINT> appid="{<GUID>}"
<IP>
:バインド用のローカル IP アドレスを指定します。 ワイルドカードのバインドは使用しないでください。 有効な IP アドレスを使用してください。<PORT>
:バインド用のポートを指定します。<THUMBPRINT>
:X.509 証明書の拇印です。<GUID>
:情報提供を目的として開発者によって生成された、アプリを表す GUID です。
参照用に、この GUID をパッケージ タグとしてアプリに格納します。
- Visual Studio での操作: [][]
- ソリューション エクスプローラー内でアプリを右クリックし、 [プロパティ] をクリックして、アプリのプロジェクト プロパティを開きます。
- [パッケージ] タブを選択します。
- 作成した GUID を [タグ] フィールドに入力します。
- Visual Studio を使用しない場合:
アプリのプロジェクト ファイルを開きます。
作成した GUID を指定した
<PackageTags>
プロパティを、新規または既存の<PropertyGroup>
に追加します。<PropertyGroup> <PackageTags>00001111-aaaa-2222-bbbb-3333cccc4444</PackageTags> </PropertyGroup>
次に例を示します。
- サーバーのローカル IP アドレスは
10.0.0.4
です。 - オンラインのランダム GUID ジェネレーターによって、
appid
の値が提供されます。
netsh http add sslcert ipport=10.0.0.4:443 certhash=b66ee04419d4ee37464ab8785ff02449980eae10 appid="{00001111-aaaa-2222-bbbb-3333cccc4444}"
証明書が登録されると、ツールから
SSL Certificate successfully added
という応答があります。証明書の登録を削除するには、
delete sslcert
コマンドを使用します。netsh http delete sslcert ipport=<IP>:<PORT>
以下は、netsh.exe のリファレンス ドキュメントです。
- Netsh Commands for Hypertext Transfer Protocol (HTTP) (ハイパーテキスト転送プロトコル (HTTP) 用の Netsh コマンド)
- UrlPrefix Strings (UrlPrefix 文字列)
アプリを実行します。
1024 より大きいポート番号で (HTTPS ではなく) HTTP を使用して localhost にバインドする場合、アプリの実行に管理者権限は必要ありません。 その他の構成の場合 (たとえば、ローカル IP アドレスを使用する場合やポート 443 にバインドする場合)、管理者権限でアプリを実行します。
サーバーのパブリック IP アドレスでアプリが応答します。 この例では、サーバーは自身のパブリック IP アドレス
104.214.79.47
でインターネットからアクセスされます。この例では開発証明書が使用されています。 証明書が信頼できないというブラウザーの警告がバイパスされた後に、ページが安全に読み込まれます。
プロキシ サーバーとロード バランサーのシナリオ
インターネットや企業ネットワークからの要求とやりとりする HTTP.sys でホストされるアプリの場合、プロキシ サーバーやロード バランサーの背後でホストするとき、追加の構成が必要になることがあります。 詳細については、「プロキシ サーバーとロード バランサーを使用するために ASP.NET Core を構成する」を参照してください。
gRPC をサポートする高度な HTTP/2 機能
HTTP.sys 内の追加の HTTP/2 機能によって、gRPC がサポートされています。これには、応答トレーラーやリセット フレームの送信に関するサポートが含まれます。
HTTP.sys で gRPC を実行するための要件:
- Windows 11 ビルド 22000 またはそれ以降、Windows Server 2022 ビルド 20348 またはそれ以降が必要です。
- TLS 1.2 またはそれ以降の接続。
予告編
HTTP トレーラーは HTTP ヘッダーに似ていますが、応答本文の送信後に送信される点が異なります。 IIS と HTTP.sys の場合は、HTTP/2 応答トレーラーのみがサポートされています。
if (httpContext.Response.SupportsTrailers())
{
httpContext.Response.DeclareTrailer("trailername");
// Write body
httpContext.Response.WriteAsync("Hello world");
httpContext.Response.AppendTrailer("trailername", "TrailerValue");
}
上記のコード例では次のようになっています。
SupportsTrailers
によって、応答におけるトレーラーが確実にサポートされます。DeclareTrailer
によって、指定したトレーラー名がTrailer
応答ヘッダーに追加されます。 応答のトレーラーを宣言することは省略可能ですが、推奨されています。DeclareTrailer
を呼び出す場合、それは、応答ヘッダーを送信する前に行う必要があります。AppendTrailer
によって、トレーラーが追加されます。
Reset
リセットを使用すると、指定されたエラー コードを使用してサーバーに HTTP/2 要求をリセットさせることができます。 リセット要求は中止されたと見なされます。
var resetFeature = httpContext.Features.Get<IHttpResetFeature>();
resetFeature.Reset(errorCode: 2);
上記のコード例の Reset
により、INTERNAL_ERROR
エラー コードが指定されています。 HTTP/2 エラー コードの詳細については、HTTP/2 仕様の「エラーコード」セクションを参照してください。
その他の技術情報
HTTP.sys は、Windows 上でのみ動作する ASP.NET Core 用 Web サーバーです。 HTTP.sys は Kestrel サーバーの代替製品であり、Kestrel では提供されていない機能がいくつか用意されています。
重要
HTTP.sys は ASP.NET Core モジュールと互換性がなく、IIS や IIS Express で使用することはできません。
HTTP.sys は、次の機能をサポートします。
- Windows 認証
- ポート共有
- SNI を使用する HTTPS
- HTTP/2 over TLS (Windows 10 以降)
- 直接ファイル伝送
- 応答キャッシュ
- WebSocket (Windows 8 以降)
サポートされている Windows バージョン:
- Windows 7 以降
- Windows Server 2008 R2 以降
サンプル コードを表示またはダウンロードします (ダウンロード方法)。
HTTP.sys を使用するタイミング
HTTP.sys は、次のような展開に適しています。
IIS を使用せず、インターネットに直接サーバーを公開する必要がある。
内部の展開から Kestrel では使用できない機能が要求されている。 詳細については、Kestrel と HTTP.sys の比較に関するページを参照してください。
HTTP.sys は、さまざまな種類の攻撃を防ぎ、フル機能の Web サーバーとして堅牢性、セキュリティ、スケーラビリティを提供する、成熟したテクノロジです。 IIS 自体が、HTTP.sys 上で HTTP リスナーとして実行されています。
HTTP/2 のサポート
Http/2 は、次の基本要件が満たされている場合に、ASP.NET Core アプリに対して有効になります。
- Windows Server 2016/Windows 10 以降
- アプリケーション レイヤー プロトコル ネゴシエーション (ALPN) 接続
- TLS 1.2 以降の接続
Http/2 接続が確立されると、HttpRequest.Protocol が HTTP/2
を報告します。
HTTP/2 は既定で有効になっています。 Http/2 接続が確立されない場合、接続は http/1.1 にフォールバックします。 Windows の今後のリリースで、HTTP.sys で HTTP/2 を無効にする機能を含む HTTP/2 構成フラグが使用可能になる予定です。
Kerberos を使用したカーネル モード認証
HTTP.sys では、Kerberos 認証プロトコルを使用したカーネル モード認証に処理が委任されます。 Kerberos および HTTP.sys ではユーザー モード認証がサポートされていません。 Active Directory から取得され、クライアントによって、ユーザーを認証するサーバーに転送される Kerberos トークン/チケットを暗号化解除するには、コンピューター アカウントを使用する必要があります。 アプリのユーザーではなく、ホストのサービス プリンシパル名 (SPN) を登録します。
HTTP.sys の使用方法
HTTP.sys を使用するように ASP.NET Core アプリを構成する
ホストを構築するときに UseHttpSys 拡張メソッドを呼び出し、必要な HttpSysOptions を指定します。 次の例では、既定値にオプションを設定しています。
public static IHostBuilder CreateHostBuilder(string[] args) =>
Host.CreateDefaultBuilder(args)
.ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.UseHttpSys(options =>
{
options.AllowSynchronousIO = false;
options.Authentication.Schemes = AuthenticationSchemes.None;
options.Authentication.AllowAnonymous = true;
options.MaxConnections = null;
options.MaxRequestBodySize = 30000000;
options.UrlPrefixes.Add("http://localhost:5005");
});
webBuilder.UseStartup<Startup>();
});
HTTP.sys の追加の構成は、レジストリ設定を通じて処理されます。
HTTP.sys オプション
プロパティ | 説明 | Default |
---|---|---|
AllowSynchronousIO | HttpContext.Request.Body および HttpContext.Response.Body に対して、入力/出力の同期を許可するかどうかを制御します。 |
false |
Authentication.AllowAnonymous | 匿名要求を許可します。 | true |
Authentication.Schemes | 許可される認証方式を指定します。 リスナーを破棄する前ならいつでも変更できます。 値は AuthenticationSchemes 列挙型 (Basic 、Kerberos 、Negotiate 、None 、および NTLM ) によって指定します。 |
None |
EnableResponseCaching | 対象となるヘッダーを持つ応答に対して、カーネル モードのキャッシュを試行します。 Set-Cookie 、Vary 、または Pragma ヘッダーを含む応答は対象外です。 応答は、public である Cache-Control ヘッダーと shared-max-age または max-age の値のいずれかを含むか、または Expires ヘッダーを含む必要があります。 |
true |
Http503Verbosity | 調整の条件によって要求を拒否する場合の HTTP.sys の動作。 | Http503VerbosityLevel. Basic |
MaxAccepts | 同時受け入れの最大数です。 | 5 × Environment. ProcessorCount |
MaxConnections | 受け入れるコンカレント接続の最大数です。 無限にするには、-1 を使用します。 コンピューター全体のレジストリ設定を使用するには、null を使用します。 |
null (コンピューター全体の 設定) |
MaxRequestBodySize | 「MaxRequestBodySize」セクションを参照してください。 | 30000000 バイト (~28.6 MB) |
RequestQueueLimit | キューに置くことができる要求の最大数。 | 1000 |
RequestQueueMode |
これは、サーバーで要求キューの作成と構成を行う必要があるかどうか、または既存のキューにアタッチする必要があるかを示します。 既存のキューにアタッチする場合、既存の構成オプションのほとんどは適用されません。 |
RequestQueueMode.Create |
RequestQueueName |
HTTP.sys 要求キューの名前。 | null (匿名キュー) |
ThrowWriteExceptions | 応答本文の書き込みがクライアントの接続の切断によって失敗した場合、例外をスローするか、または正常に完了するかどうかを指定します。 | false (正常に完了する) |
Timeouts | HTTP.sys TimeoutManager 構成を公開します。これはレジストリでも構成できます。 各設定に関する既定値などの詳細については、API のリンクを参照してください。
|
|
UrlPrefixes | HTTP.sys に登録する UrlPrefixCollection を指定します。 最も便利なのは UrlPrefixCollection.Add です。これを使用して、コレクションにプレフィックスを追加できます。 これらは、リスナーを破棄する前ならいつでも変更できます。 |
MaxRequestBodySize
要求本文の最大許容サイズ (バイト単位) です。 null
に設定する場合、要求本文の最大サイズは制限されません。 この制限は、アップグレード済みの接続 (常に無制限) には影響しません。
1 つの IActionResult
に対する ASP.NET Core MVC アプリの制限をオーバーライドする方法として、アクション メソッドに対して RequestSizeLimitAttribute 属性を使用することをお勧めします。
[RequestSizeLimit(100000000)]
public IActionResult MyActionMethod()
アプリが要求の読み取りを開始した後に、アプリが要求に対する制限を構成しようとすると、例外がスローされます。 IsReadOnly
プロパティを使用して、MaxRequestBodySize
プロパティが読み取り専用状態にあるかどうか、つまり制限を構成するには遅すぎるかどうかを示すことができます。
要求ごとにアプリで MaxRequestBodySize をオーバーライドする必要がある場合は、IHttpMaxRequestBodySizeFeature を使います。
public void Configure(IApplicationBuilder app, IWebHostEnvironment env,
ILogger<Startup> logger, IServer server)
{
app.Use(async (context, next) =>
{
context.Features.Get<IHttpMaxRequestBodySizeFeature>()
.MaxRequestBodySize = 10 * 1024;
var serverAddressesFeature =
app.ServerFeatures.Get<IServerAddressesFeature>();
var addresses = string.Join(", ", serverAddressesFeature?.Addresses);
logger.LogInformation("Addresses: {Addresses}", addresses);
await next.Invoke();
});
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
else
{
app.UseExceptionHandler("/Error");
}
app.UseStaticFiles();
app.UseRouting();
app.UseEndpoints(endpoints =>
{
endpoints.MapRazorPages();
});
}
Visual Studio を使用する場合は、アプリが IIS または IIS Express を実行するように構成されていないことを確認します。
Visual Studio では、既定の起動プロファイルは IIS Express 用です。 プロジェクトをコンソール アプリとして実行するには、次のスクリーン ショットに示すように、選択したプロファイルを手動で変更します。
Windows Server を構成する
アプリに対して開くポートを決めたら、Windows ファイアウォールか New-NetFirewallRule PowerShell コマンドレットを使用して、トラフィックが HTTP.sys に到達できるようにファイアウォールのポートを開きます。 次のコマンドとアプリの構成では、ポート 443 を使用します。
Azure VM に展開する場合は、ネットワーク セキュリティ グループ内でポートを開きます。 次のコマンドとアプリの構成では、ポート 443 を使用します。
必要に応じて、X.509 証明書を取得してインストールします。
Windows の場合は、New-SelfSignedCertificate PowerShell コマンドレットを使用して自己署名証明書を作成します。 サポート対象外の例については、UpdateIISExpressSSLForChrome.ps1 を参照してください。
自己署名証明書か CA 署名証明書のいずれかをサーバーの Local Machine>Personal ストアにインストールします。
アプリがフレームワークに依存する展開である場合は、.NET Core、.NET Framework、またはその両方 (アプリが .NET Framework をターゲットとする .NET Core アプリである場合) をインストールします。
- .NET Core: アプリで .NET Core が必要な場合は、.NET Core のダウンロードから .NET Core Runtime インストーラーを取得して実行します。 サーバーに SDK 全体をインストールしないでください。
- .NET Framework:アプリで .NET Framework が必要な場合は、.NET Framework のインストール ガイドを参照してください。 必要な .NET Framework をインストールします。 最新の .NET Framework のインストーラーは .NET Core のダウンロード ページから入手できます。
アプリが自己完結型の展開の場合、アプリの展開内にランタイムが含まれています。 サーバーにフレームワークをインストールする必要はありません。
アプリに URL とポートを構成します。
既定では、ASP.NET Core は
http://localhost:5000
にバインドされます。 URL プレフィックスとポートを構成するには、次のオプションがあります。- UseUrls
urls
コマンド ライン引数ASPNETCORE_URLS
環境変数- UrlPrefixes
次のコード例は、サーバーのローカル IP アドレス
10.0.0.4
を使ってポート 443 上で UrlPrefixes を使う方法を示しています。public static IHostBuilder CreateHostBuilder(string[] args) => Host.CreateDefaultBuilder(args) .ConfigureWebHostDefaults(webBuilder => { webBuilder.UseHttpSys(options => { options.UrlPrefixes.Add("https://10.0.0.4:443"); }); webBuilder.UseStartup<Startup>(); });
UrlPrefixes
の利点は、プレフィックスの形式が正しくなかった場合、すぐにエラー メッセージが生成されることです。UrlPrefixes
の設定はUseUrls
/urls
/ASPNETCORE_URLS
の設定をオーバーライドします。 したがって、UseUrls
、urls
、およびASPNETCORE_URLS
環境変数の利点は、Kestrel と HTTP.sys を簡単に切り替えられることです。HTTP.sys では、HTTP サーバー API の UrlPrefix 文字列形式が使用されます。
警告
最上位のワイルドカードのバインド (
http://*:80/
とhttp://+:80
) は使用しては いけません 。 最上位のワイルドカードのバインドを使用すると、アプリにセキュリティの脆弱性が生じます。 これは、強力と脆弱の両方のワイルドカードに適用されます。 ワイルドカードではなく、明示的なホスト名か IP アドレスを使用してください。 親ドメイン全体を制御する場合、サブドメインのワイルドカードのバインド (たとえば、*.mysub.com
) がセキュリティ リスクになることはありません (脆弱である*.com
とは対照的)。 詳細については、RFC 9110: セクション 7.2: 「Host and :authority (ホストと :authority)」を参照してください。サーバーで URL プレフィックスを事前登録します。
HTTP.sys を構成するための組み込みツールは、netsh.exe です。 netsh.exe を使用して、URL プレフィックスを予約し、X.509 証明書を割り当てることができます。 ツールを使用するには管理者特権が必要です。
netsh.exe ツールを使用して、アプリ用に URL を登録します。
netsh http add urlacl url=<URL> user=<USER>
<URL>
:完全修飾 URL (Uniform Resource Locator)。 ワイルドカードのバインドは使用しないでください。 有効なホスト名かローカル IP アドレスを使用してください。 "URL の末尾にはスラッシュが必要です。 "<USER>
:ユーザーまたはユーザー グループの名前を指定します。
次の例では、サーバーのローカル IP アドレスは
10.0.0.4
です。netsh http add urlacl url=https://10.0.0.4:443/ user=Users
URL が登録されると、ツールから
URL reservation successfully added
という応答があります。登録済みの URL を削除するには、
delete urlacl
コマンドを使用します。netsh http delete urlacl url=<URL>
サーバーで X.509 証明書を登録します。
netsh.exe ツールを使用して、アプリ用の証明書を登録します。
netsh http add sslcert ipport=<IP>:<PORT> certhash=<THUMBPRINT> appid="{<GUID>}"
<IP>
:バインド用のローカル IP アドレスを指定します。 ワイルドカードのバインドは使用しないでください。 有効な IP アドレスを使用してください。<PORT>
:バインド用のポートを指定します。<THUMBPRINT>
:X.509 証明書の拇印です。<GUID>
:情報提供を目的として開発者によって生成された、アプリを表す GUID です。
参照用に、この GUID をパッケージ タグとしてアプリに格納します。
- Visual Studio での操作: [][]
- ソリューション エクスプローラー内でアプリを右クリックし、 [プロパティ] をクリックして、アプリのプロジェクト プロパティを開きます。
- [パッケージ] タブを選択します。
- 作成した GUID を [タグ] フィールドに入力します。
- Visual Studio を使用しない場合:
アプリのプロジェクト ファイルを開きます。
作成した GUID を指定した
<PackageTags>
プロパティを、新規または既存の<PropertyGroup>
に追加します。<PropertyGroup> <PackageTags>00001111-aaaa-2222-bbbb-3333cccc4444</PackageTags> </PropertyGroup>
次に例を示します。
- サーバーのローカル IP アドレスは
10.0.0.4
です。 - オンラインのランダム GUID ジェネレーターによって、
appid
の値が提供されます。
netsh http add sslcert ipport=10.0.0.4:443 certhash=b66ee04419d4ee37464ab8785ff02449980eae10 appid="{00001111-aaaa-2222-bbbb-3333cccc4444}"
証明書が登録されると、ツールから
SSL Certificate successfully added
という応答があります。証明書の登録を削除するには、
delete sslcert
コマンドを使用します。netsh http delete sslcert ipport=<IP>:<PORT>
以下は、netsh.exe のリファレンス ドキュメントです。
- Netsh Commands for Hypertext Transfer Protocol (HTTP) (ハイパーテキスト転送プロトコル (HTTP) 用の Netsh コマンド)
- UrlPrefix Strings (UrlPrefix 文字列)
アプリを実行します。
1024 より大きいポート番号で (HTTPS ではなく) HTTP を使用して localhost にバインドする場合、アプリの実行に管理者権限は必要ありません。 その他の構成の場合 (たとえば、ローカル IP アドレスを使用する場合やポート 443 にバインドする場合)、管理者権限でアプリを実行します。
サーバーのパブリック IP アドレスでアプリが応答します。 この例では、サーバーは自身のパブリック IP アドレス
104.214.79.47
でインターネットからアクセスされます。この例では開発証明書が使用されています。 証明書が信頼できないというブラウザーの警告がバイパスされた後に、ページが安全に読み込まれます。
プロキシ サーバーとロード バランサーのシナリオ
インターネットや企業ネットワークからの要求とやりとりする HTTP.sys でホストされるアプリの場合、プロキシ サーバーやロード バランサーの背後でホストするとき、追加の構成が必要になることがあります。 詳細については、「プロキシ サーバーとロード バランサーを使用するために ASP.NET Core を構成する」を参照してください。
gRPC をサポートする高度な HTTP/2 機能
HTTP.sys 内の追加の HTTP/2 機能によって、gRPC がサポートされています。これには、応答トレーラーやリセット フレームの送信に関するサポートが含まれます。
HTTP.sys で gRPC を実行するための要件:
- Windows 10、OS Build 19041.508 以降
- TLS 1.2 以降の接続
予告編
HTTP トレーラーは HTTP ヘッダーに似ていますが、応答本文の送信後に送信される点が異なります。 IIS と HTTP.sys の場合は、HTTP/2 応答トレーラーのみがサポートされています。
if (httpContext.Response.SupportsTrailers())
{
httpContext.Response.DeclareTrailer("trailername");
// Write body
httpContext.Response.WriteAsync("Hello world");
httpContext.Response.AppendTrailer("trailername", "TrailerValue");
}
上記のコード例では次のようになっています。
SupportsTrailers
によって、応答におけるトレーラーが確実にサポートされます。DeclareTrailer
によって、指定したトレーラー名がTrailer
応答ヘッダーに追加されます。 応答のトレーラーを宣言することは省略可能ですが、推奨されています。DeclareTrailer
を呼び出す場合、それは、応答ヘッダーを送信する前に行う必要があります。AppendTrailer
によって、トレーラーが追加されます。
Reset
リセットを使用すると、指定されたエラー コードを使用してサーバーに HTTP/2 要求をリセットさせることができます。 リセット要求は中止されたと見なされます。
var resetFeature = httpContext.Features.Get<IHttpResetFeature>();
resetFeature.Reset(errorCode: 2);
上記のコード例の Reset
により、INTERNAL_ERROR
エラー コードが指定されています。 HTTP/2 エラー コードの詳細については、HTTP/2 仕様の「エラーコード」セクションを参照してください。
その他の技術情報
ASP.NET Core