.NET でのサービス検出
この記事では、Microsoft.Extensions.ServiceDiscovery
ライブラリの使用方法について説明します。 サービス検出は、開発者が物理アドレス (IP アドレスとポート) の代わりに論理名を使って外部サービスを参照するための方法です。
作業の開始
.NET でサービス検出を使い始めるには、Microsoft.Extensions.ServiceDiscovery NuGet パッケージをインストールします。
dotnet add package Microsoft.Extensions.ServiceDiscovery --prerelease
詳しくは、「dotnet add package」または「.NET アプリケーションでパッケージの依存関係を管理する」をご覧ください。
使用例
プロジェクトの Program.cs ファイルで、AddServiceDiscovery 拡張メソッドを呼び出してサービス検出をホストに追加し、既定のサービス エンドポイント リゾルバーを構成します。
builder.Services.AddServiceDiscovery();
AddServiceDiscovery
拡張メソッドを呼び出して、個々の IHttpClientBuilder にサービス検出を追加します。
builder.Services.AddHttpClient<CatalogServiceClient>(static client =>
{
client.BaseAddress = new("https://catalog");
})
.AddServiceDiscovery();
または、既定ですべての HttpClient インスタンスにサービス検出を追加することもできます。
builder.Services.ConfigureHttpClientDefaults(static http =>
{
// Turn on service discovery by default
http.AddServiceDiscovery();
});
HTTP エンドポイントを解決する際のスキームの選択
サービスをローカルで開発およびテストするときには HTTP を使用し、そのサービスをデプロイするときには HTTPS を使用するのが一般的です。 サービス検出では、サービス検出に与えられる入力文字列で URI スキームの優先度リストを指定できるようにして、これをサポートしています。 サービス検出は、スキームのサービスの解決を順番に試行し、エンドポイントが見つかると停止します。 URI スキームは +
文字で区切られます (例: "https+http://basket"
)。 サービス検出は、まず "basket"
サービスの HTTPS エンドポイントの検出を試み、次に HTTP エンドポイントにフォールバックします。 HTTPS エンドポイントが見つかると、サービス検出に HTTP エンドポイントは含まれません。
ServiceDiscoveryOptions
で AllowedSchemes
プロパティと AllowAllSchemes
プロパティを構成すると、スキームをフィルター処理できます。 すべてのスキームが許可されることを示すには、AllowAllSchemes
プロパティを使用します。 既定では、AllowAllSchemes
は true
に設定され、すべてのスキームが許可されます。 AllowAllSchemes
を false
に設定し、許可されるスキームを AllowedSchemes
プロパティに追加すると、スキームを制限できます。 たとえば、HTTPS のみを許可するには、次のようにします。
services.Configure<ServiceDiscoveryOptions>(options =>
{
options.AllowAllSchemes = false;
options.AllowedSchemes = ["https"];
});
すべてのスキームを明示的に許可するには、ServiceDiscoveryOptions.AllowAllSchemes
プロパティを true
に設定します。
services.Configure<ServiceDiscoveryOptions>(
options => options.AllowAllSchemes = true);
構成からサービス エンドポイントを解決する
AddServiceDiscovery
拡張メソッドは、既定で構成ベースのエンドポイント リゾルバーを追加します。
このリゾルバーは、.NET 構成システムからエンドポイントを読み取ります。 このライブラリでは、appsettings.json、環境変数、または他の任意の IConfiguration ソースからの構成がサポートされています。
次に示すのは、appsettings.json
を使って catalog という名前のサービスのエンドポイントを構成する方法の例です。
{
"Services": {
"catalog": {
"https": [
"localhost:8080",
"10.46.24.90:80"
]
}
}
}
前の例では、catalog という名前のサービスに対して、https://localhost:8080
と "https://10.46.24.90:80"
の 2 つのエンドポイントが追加されます。 catalog が解決されるたびに、これらのエンドポイントのいずれかが選ばれます。
IServiceCollection で AddServiceDiscoveryCore 拡張メソッドを使ってサービス検出をホストに追加した場合は、IServiceCollection
で AddConfigurationServiceEndpointProvider 拡張メソッドを呼び出すことにより、構成ベースのエンドポイント リゾルバーを追加できます。
構成
構成リゾルバーを構成するには、次の構成オプションを備える ConfigurationServiceEndpointProviderOptions クラスを使います。
SectionName: サービス エンドポイントを含む構成セクションの名前。 既定値は
"Services"
です。ApplyHostNameMetadata: 解決されたエンドポイントにホスト名メタデータを適用するかどうかを決定するために使われるデリゲート。 既定では、
false
を返す関数です。
これらのオプションを構成するには、アプリケーションの Startup
クラスまたは Program
ファイル内の IServiceCollection
で Configure
拡張メソッドを使用できます。
var builder = WebApplication.CreateBuilder(args);
builder.Services.Configure<ConfigurationServiceEndPointResolverOptions>(
static options =>
{
options.SectionName = "MyServiceEndpoints";
// Configure the logic for applying host name metadata
options.ApplyHostNameMetadata = static endpoint =>
{
// Your custom logic here. For example:
return endpoint.EndPoint is DnsEndPoint dnsEp
&& dnsEp.Host.StartsWith("internal");
};
});
前に示した例では、サービス エンドポイントに対してカスタム セクション名を設定し、ホスト名メタデータを適用するためのカスタム条件ロジックを提供しています。
プラットフォーム提供のサービス検出を使用してサービス エンドポイントを解決する
Azure Container Apps や Kubernetes (適切に構成されている場合) などの特定のプラットフォームでは、サービス検出クライアント ライブラリを必要とせずにサービス検出機能が提供されます。 そのような環境にアプリケーションがデプロイされている場合は、プラットフォームの組み込み機能を使うと便利です。 パススルー リゾルバーは、このシナリオを容易にするように設計されています。 それを使うと、開発者のコンピューターなどのさまざまな環境で、構成などの代替リゾルバーを利用できます。 重要なのは、この柔軟性を実現するために、コードの変更や条件付きガードの実装が必要ないことです。
パススルー リゾルバーは外部解決を実行せず、代わりに、DnsEndPoint と表される入力サービス名を返すことによってエンドポイントを解決します。
パススルー プロバイダーは、AddServiceDiscovery
拡張メソッドを使ってサービス検出を追加すると、既定で構成されます。
IServiceCollection
で AddServiceDiscoveryCore
拡張メソッドを使ってサービス検出をホストに追加した場合は、IServiceCollection
で AddPassThroughServiceEndpointProvider 拡張メソッドを呼び出すことにより、パススルー プロバイダーを追加できます。
関連項目
.NET