Auswählen zwischen controllerbasierten APIs und minimalen APIs

Hinweis

Dies ist nicht die neueste Version dieses Artikels. Informationen zum aktuellen Release finden Sie in der .NET 8-Version dieses Artikels.

Wichtig

Diese Informationen beziehen sich auf ein Vorabversionsprodukt, das vor der kommerziellen Freigabe möglicherweise noch wesentlichen Änderungen unterliegt. Microsoft gibt keine Garantie, weder ausdrücklich noch impliziert, hinsichtlich der hier bereitgestellten Informationen.

Informationen zum aktuellen Release finden Sie in der .NET 8-Version dieses Artikels.

ASP.NET Core unterstützt zwei Ansätze beim Erstellen von APIs: einen controllerbasierten Ansatz und minimale APIs. Controller in einem API-Projekt sind Klassen, die von ControllerBase abgeleitet werden. Minimale APIs definieren Endpunkte mit logischen Handlern in Lambdas oder Methoden. In diesem Artikel werden die Unterschiede zwischen den beiden Ansätzen erläutert.

Bei minimalen APIs wird die Hostklasse standardmäßig verborgen, und der Fokus liegt auf der Konfiguration und Erweiterbarkeit über Erweiterungsmethoden, die Funktionen als Lambda-Ausdrücke akzeptieren. Controller sind Klassen, die Abhängigkeiten über Konstruktor- oder Eigenschafteneinfügung akzeptieren und ganz allgemein objektorientierten Mustern folgen. Minimale APIs unterstützen die Einfügung von Abhängigkeiten durch andere Ansätze, z. B. durch Zugriff auf den Dienstanbieter.

Hier sehen Sie Beispielcode für eine API, die auf Controllern basiert:


namespace APIWithControllers;

public class Program
{
    public static void Main(string[] args)
    {
        var builder = WebApplication.CreateBuilder(args);

        builder.Services.AddControllers();
        var app = builder.Build();

        app.UseHttpsRedirection();

        app.MapControllers();

        app.Run();
    }
}
using Microsoft.AspNetCore.Mvc;

namespace APIWithControllers.Controllers;
[ApiController]
[Route("[controller]")]
public class WeatherForecastController : ControllerBase
{
    private static readonly string[] Summaries = new[]
    {
        "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
    };

    private readonly ILogger<WeatherForecastController> _logger;

    public WeatherForecastController(ILogger<WeatherForecastController> logger)
    {
        _logger = logger;
    }

    [HttpGet(Name = "GetWeatherForecast")]
    public IEnumerable<WeatherForecast> Get()
    {
        return Enumerable.Range(1, 5).Select(index => new WeatherForecast
        {
            Date = DateOnly.FromDateTime(DateTime.Now.AddDays(index)),
            TemperatureC = Random.Shared.Next(-20, 55),
            Summary = Summaries[Random.Shared.Next(Summaries.Length)]
        })
        .ToArray();
    }
}

Der folgende Code stellt die gleiche Funktionalität in einem minimalen API-Projekt bereit. Beachten Sie, dass beim minimalen API-Ansatz der zugehörige Codes in Lambda-Ausdrücken eingeschlossen wird.


namespace MinimalAPI;

public class Program
{
    public static void Main(string[] args)
    {
        var builder = WebApplication.CreateBuilder(args);

        var app = builder.Build();

        app.UseHttpsRedirection();

        var summaries = new[]
        {
            "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
        };

        app.MapGet("/weatherforecast", (HttpContext httpContext) =>
        {
            var forecast = Enumerable.Range(1, 5).Select(index =>
                new WeatherForecast
                {
                    Date = DateOnly.FromDateTime(DateTime.Now.AddDays(index)),
                    TemperatureC = Random.Shared.Next(-20, 55),
                    Summary = summaries[Random.Shared.Next(summaries.Length)]
                })
                .ToArray();
            return forecast;
        });

        app.Run();
    }
}

Beide API-Projekte verweisen auf die folgende Klasse:

namespace APIWithControllers;

public class WeatherForecast
{
    public DateOnly Date { get; set; }

    public int TemperatureC { get; set; }

    public int TemperatureF => 32 + (int)(TemperatureC / 0.5556);

    public string? Summary { get; set; }
}

Minimale APIs besitzen viele der gleichen Funktionen wie controllerbasierte APIs. Sie unterstützen die Konfiguration und Anpassung, die für eine Skalierung auf mehrere APIs, die Verarbeitung komplexer Routen, die Anwendung von Autorisierungsregeln und die Steuerung des Inhalts von API-Antworten erforderlich sind. Einige Funktionen sind mit controllerbasierten APIs verfügbar, werden aber noch nicht von minimalen APIs unterstützt oder von diesen implementiert. Dazu gehören:

  • Keine integrierte Unterstützung für die Modellbindung (IModelBinderProvider, IModelBinder). Unterstützung kann mit einem benutzerdefinierten Bindungs-Shim hinzugefügt werden.
  • Keine integrierte Unterstützung für die Validierung (IModelValidator).
  • Keine Unterstützung für Anwendungsparts oder das Anwendungsmodell. Es gibt keine Möglichkeit, eigene Konventionen anzuwenden oder zu erstellen.
  • Keine integrierte Unterstützung für das Ansichtsrendering. Es wird empfohlen, Razor Pages zum Rendern von Ansichten zu verwenden.
  • Keine Unterstützung für JsonPatch.
  • Keine Unterstützung für OData.

Weitere Informationen

ASP.NET Core unterstützt zwei Ansätze beim Erstellen von APIs: einen controllerbasierten Ansatz und minimale APIs. Controller in einem API-Projekt sind Klassen, die von ControllerBase abgeleitet werden. Minimale APIs definieren Endpunkte mit logischen Handlern in Lambdas oder Methoden. In diesem Artikel werden die Unterschiede zwischen den beiden Ansätzen erläutert.

Bei minimalen APIs wird die Hostklasse standardmäßig verborgen, und der Fokus liegt auf der Konfiguration und Erweiterbarkeit über Erweiterungsmethoden, die Funktionen als Lambda-Ausdrücke akzeptieren. Controller sind Klassen, die Abhängigkeiten über Konstruktor- oder Eigenschafteneinfügung akzeptieren und ganz allgemein objektorientierten Mustern folgen. Minimale APIs unterstützen die Einfügung von Abhängigkeiten durch andere Ansätze, z. B. durch Zugriff auf den Dienstanbieter.

Hier sehen Sie Beispielcode für eine API, die auf Controllern basiert:


namespace APIWithControllers;

public class Program
{
    public static void Main(string[] args)
    {
        var builder = WebApplication.CreateBuilder(args);

        builder.Services.AddControllers();
        var app = builder.Build();

        app.UseHttpsRedirection();

        app.MapControllers();

        app.Run();
    }
}
using Microsoft.AspNetCore.Mvc;

namespace APIWithControllers.Controllers;
[ApiController]
[Route("[controller]")]
public class WeatherForecastController : ControllerBase
{
    private static readonly string[] Summaries = new[]
    {
        "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
    };

    private readonly ILogger<WeatherForecastController> _logger;

    public WeatherForecastController(ILogger<WeatherForecastController> logger)
    {
        _logger = logger;
    }

    [HttpGet(Name = "GetWeatherForecast")]
    public IEnumerable<WeatherForecast> Get()
    {
        return Enumerable.Range(1, 5).Select(index => new WeatherForecast
        {
            Date = DateOnly.FromDateTime(DateTime.Now.AddDays(index)),
            TemperatureC = Random.Shared.Next(-20, 55),
            Summary = Summaries[Random.Shared.Next(Summaries.Length)]
        })
        .ToArray();
    }
}

Der folgende Code stellt die gleiche Funktionalität in einem minimalen API-Projekt bereit. Beachten Sie, dass beim minimalen API-Ansatz der zugehörige Codes in Lambda-Ausdrücken eingeschlossen wird.


namespace MinimalAPI;

public class Program
{
    public static void Main(string[] args)
    {
        var builder = WebApplication.CreateBuilder(args);

        var app = builder.Build();

        app.UseHttpsRedirection();

        var summaries = new[]
        {
            "Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
        };

        app.MapGet("/weatherforecast", (HttpContext httpContext) =>
        {
            var forecast = Enumerable.Range(1, 5).Select(index =>
                new WeatherForecast
                {
                    Date = DateOnly.FromDateTime(DateTime.Now.AddDays(index)),
                    TemperatureC = Random.Shared.Next(-20, 55),
                    Summary = summaries[Random.Shared.Next(summaries.Length)]
                })
                .ToArray();
            return forecast;
        });

        app.Run();
    }
}

Beide API-Projekte verweisen auf die folgende Klasse:

namespace APIWithControllers;

public class WeatherForecast
{
    public DateOnly Date { get; set; }

    public int TemperatureC { get; set; }

    public int TemperatureF => 32 + (int)(TemperatureC / 0.5556);

    public string? Summary { get; set; }
}

Minimale APIs besitzen viele der gleichen Funktionen wie controllerbasierte APIs. Sie unterstützen die Konfiguration und Anpassung, die für eine Skalierung auf mehrere APIs, die Verarbeitung komplexer Routen, die Anwendung von Autorisierungsregeln und die Steuerung des Inhalts von API-Antworten erforderlich sind. Einige Funktionen sind mit controllerbasierten APIs verfügbar, werden aber noch nicht von minimalen APIs unterstützt oder von diesen implementiert. Dazu gehören:

  • Keine integrierte Unterstützung für die Modellbindung (IModelBinderProvider, IModelBinder). Unterstützung kann mit einem benutzerdefinierten Bindungs-Shim hinzugefügt werden.
  • Keine Unterstützung für die Bindung aus Formularen. Dies schließt die Bindung IFormFile ein.
  • Keine integrierte Unterstützung für die Validierung (IModelValidator).
  • Keine Unterstützung für Anwendungsparts oder das Anwendungsmodell. Es gibt keine Möglichkeit, eigene Konventionen anzuwenden oder zu erstellen.
  • Keine integrierte Unterstützung für das Ansichtsrendering. Es wird empfohlen, Razor Pages zum Rendern von Ansichten zu verwenden.
  • Keine Unterstützung für JsonPatch.
  • Keine Unterstützung für OData.

Weitere Informationen