カスタム ASP.NET Core ミドルウェアを記述するWrite custom ASP.NET Core middleware

作成者: Rick AndersonSteve SmithBy Rick Anderson and Steve Smith

ミドルウェアとは、要求と応答を処理するために、アプリのパイプラインに組み込まれたソフトウェアです。Middleware is software that's assembled into an app pipeline to handle requests and responses. ASP.NET Core からは、組み込みミドルウェア コンポーネントが豊富に提供されますが、カスタム ミドルウェアを記述したほうが良い場合もあります。ASP.NET Core provides a rich set of built-in middleware components, but in some scenarios you might want to write a custom middleware.

注意

このトピックでは "規約に基づく" ミドルウェアを作成する方法について説明します。This topic describes how to write convention-based middleware. 厳密な型指定と要求ごとのアクティベーションを使用したアプローチについては、「ASP.NET Core でのファクトリ ベースのミドルウェアのアクティブ化」を参照してください。For an approach that uses strong typing and per-request activation, see ASP.NET Core でのファクトリ ベースのミドルウェアのアクティブ化.

ミドルウェア クラスMiddleware class

ミドルウェアは一般に、クラスにカプセル化され、拡張メソッドを使用して公開されます。Middleware is generally encapsulated in a class and exposed with an extension method. クエリ文字列から現在の要求のカルチャを設定する次のようなミドルウェアを考慮します。Consider the following middleware, which sets the culture for the current request from a query string:

public class Startup
{
    public void Configure(IApplicationBuilder app)
    {
        app.Use(async (context, next) =>
        {
            var cultureQuery = context.Request.Query["culture"];
            if (!string.IsNullOrWhiteSpace(cultureQuery))
            {
                var culture = new CultureInfo(cultureQuery);

                CultureInfo.CurrentCulture = culture;
                CultureInfo.CurrentUICulture = culture;
            }

            // Call the next delegate/middleware in the pipeline
            await next();
        });

        app.Run(async (context) =>
        {
            await context.Response.WriteAsync(
                $"Hello {CultureInfo.CurrentCulture.DisplayName}");
        });

    }
}

上のサンプル コードを使って、ミドルウェア コンポーネントの作成方法を示します。The preceding sample code is used to demonstrate creating a middleware component. ASP.NET Core に組み込まれているローカライズのサポートについては、「ASP.NET Core のグローバリゼーションおよびローカリゼーション」を参照してください。For ASP.NET Core's built-in localization support, see ASP.NET Core のグローバリゼーションおよびローカリゼーション.

カルチャを渡すことによって、ミドルウェアをテストします。Test the middleware by passing in the culture. たとえば、https://localhost:5001/?culture=no を要求します。For example, request https://localhost:5001/?culture=no.

次のコードは、ミドルウェアのデリゲートをクラスに移動します。The following code moves the middleware delegate to a class:

using Microsoft.AspNetCore.Http;
using System.Globalization;
using System.Threading.Tasks;

namespace Culture
{
    public class RequestCultureMiddleware
    {
        private readonly RequestDelegate _next;

        public RequestCultureMiddleware(RequestDelegate next)
        {
            _next = next;
        }

        public async Task InvokeAsync(HttpContext context)
        {
            var cultureQuery = context.Request.Query["culture"];
            if (!string.IsNullOrWhiteSpace(cultureQuery))
            {
                var culture = new CultureInfo(cultureQuery);

                CultureInfo.CurrentCulture = culture;
                CultureInfo.CurrentUICulture = culture;

            }

            // Call the next delegate/middleware in the pipeline
            await _next(context);
        }
    }
}

ミドルウェアのクラスには、次のものが含まれる必要があります。The middleware class must include:

  • RequestDelegate 型のパラメーターを持つパブリック コンストラクター。A public constructor with a parameter of type RequestDelegate.
  • Invoke または InvokeAsync という名前のパブリック メソッド。A public method named Invoke or InvokeAsync. このメソッドでは次のことが必要です。This method must:
    • Task を返します。Return a Task.
    • HttpContext 型の最初のパラメーターを受け取ります。Accept a first parameter of type HttpContext.

コンストラクターおよび Invoke/InvokeAsync に対する追加のパラメーターは、依存関係の挿入 (DI) によって設定されます。Additional parameters for the constructor and Invoke/InvokeAsync are populated by dependency injection (DI).

ミドルウェアの依存関係Middleware dependencies

ミドルウェアは、コンストラクターで依存関係を公開することによって、明示的な依存関係の原則に従う必要があります。Middleware should follow the Explicit Dependencies Principle by exposing its dependencies in its constructor. ミドルウェアは、"アプリケーションの有効期間" ごとに 1 回構築されます。Middleware is constructed once per application lifetime. 要求内でミドルウェアとサービスを共有する必要がある場合は、「要求ごとのミドルウェアの依存関係」セクションをご覧ください。See the Per-request middleware dependencies section if you need to share services with middleware within a request.

ミドルウェア コンポーネントは、コンストラクター パラメーターにより、依存関係の挿入 (DI) から依存関係を解決できます。Middleware components can resolve their dependencies from dependency injection (DI) through constructor parameters. UseMiddleware<T> は、追加パラメーターを直接受け入れることもできます。UseMiddleware<T> can also accept additional parameters directly.

要求ごとのミドルウェアの依存関係Per-request middleware dependencies

ミドルウェアは要求ごとではなくアプリの起動時に構築されるため、ミドルウェアのコンストラクターによって使われる "スコープ" 有効期間のサービスは、各要求の間に、依存関係によって挿入される他の種類と共有されません。Because middleware is constructed at app startup, not per-request, scoped lifetime services used by middleware constructors aren't shared with other dependency-injected types during each request. ミドルウェアとその他の種類の間で "スコープ" サービスを共有する必要がある場合は、これらのサービスを Invoke メソッドのシグネチャに追加します。If you must share a scoped service between your middleware and other types, add these services to the Invoke method's signature. Invoke メソッドは、DI によって設定される追加のパラメーターを受け取ることができます。The Invoke method can accept additional parameters that are populated by DI:

public class CustomMiddleware
{
    private readonly RequestDelegate _next;

    public CustomMiddleware(RequestDelegate next)
    {
        _next = next;
    }

    // IMyScopedService is injected into Invoke
    public async Task Invoke(HttpContext httpContext, IMyScopedService svc)
    {
        svc.MyProperty = 1000;
        await _next(httpContext);
    }
}

ミドルウェア拡張メソッドMiddleware extension method

次の拡張メソッドは、IApplicationBuilder を介してミドルウェアを公開します。The following extension method exposes the middleware through IApplicationBuilder:

using Microsoft.AspNetCore.Builder;

namespace Culture
{
    public static class RequestCultureMiddlewareExtensions
    {
        public static IApplicationBuilder UseRequestCulture(
            this IApplicationBuilder builder)
        {
            return builder.UseMiddleware<RequestCultureMiddleware>();
        }
    }
}

次のコードは、Startup.Configure からミドルウェアを呼び出します。The following code calls the middleware from Startup.Configure:

public class Startup
{
    public void Configure(IApplicationBuilder app)
    {
        app.UseRequestCulture();

        app.Run(async (context) =>
        {
            await context.Response.WriteAsync(
                $"Hello {CultureInfo.CurrentCulture.DisplayName}");
        });
    }
}

その他の技術情報Additional resources