在基于控制器的 API 和最小 API 之间进行选择
注意
此版本不是本文的最新版本。 对于当前版本,请参阅此文的 .NET 8 版本。
警告
此版本的 ASP.NET Core 不再受支持。 有关详细信息,请参阅 .NET 和 .NET Core 支持策略。 对于当前版本,请参阅此文的 .NET 8 版本。
ASP.NET Core 支持两种创建 API 的方法:基于控制器的方法和最小 API。 API 项目中的控制器是派生自 ControllerBase 的类。 最小 API 在 Lambda 或方法中使用逻辑处理程序定义终结点。 本文解释了这两种方法之间的差异。
最小 API 的设计默认隐藏了主机类,并通过将函数作为 Lambda 表达式的扩展方法专注于配置和扩展性。 控制器是可以通过构造函数注入或属性注入采用依赖关系的类,通常遵循面向对象的模式。 最小 API 通过访问服务提供程序等一系列其他方法支持依赖关系注入。
下面是基于控制器的 API 的示例代码:
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();
}
}
下面的代码在最小 API 项目中提供了相同的功能。 请注意,最小 API 方法涉及在 Lambda 表达式中包含相关代码。
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();
}
}
两个 API 项目都引用以下类:
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; }
}
最小 API 具有许多与基于控制器的 API 相同的功能。 它们支持缩放到多个 API、处理复杂路由、应用授权规则和控制 API 响应内容所需的配置和自定义。 基于控制器的 API 有一些功能还没有被最小 API 所支持或实现。 其中包括:
- 不提供对模型绑定的内置支持(IModelBinderProvider、IModelBinder)。 可以使用自定义绑定填充码添加支持。
- 不提供对验证的内置支持 (IModelValidator)。
- 不支持应用程序部件或应用程序模型。 无法应用或生成自己的约定。
- 没有内置视图呈现支持。 建议使用 Razor Pages 呈现视图。
- 不支持 JsonPatch
- 不支持 OData
另请参阅
ASP.NET Core 支持两种创建 API 的方法:基于控制器的方法和最小 API。 API 项目中的控制器是派生自 ControllerBase 的类。 最小 API 在 Lambda 或方法中使用逻辑处理程序定义终结点。 本文解释了这两种方法之间的差异。
最小 API 的设计默认隐藏了主机类,并通过将函数作为 Lambda 表达式的扩展方法专注于配置和扩展性。 控制器是可以通过构造函数注入或属性注入采用依赖关系的类,通常遵循面向对象的模式。 最小 API 通过访问服务提供程序等一系列其他方法支持依赖关系注入。
下面是基于控制器的 API 的示例代码:
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();
}
}
下面的代码在最小 API 项目中提供了相同的功能。 请注意,最小 API 方法涉及在 Lambda 表达式中包含相关代码。
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();
}
}
两个 API 项目都引用以下类:
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; }
}
最小 API 具有许多与基于控制器的 API 相同的功能。 它们支持缩放到多个 API、处理复杂路由、应用授权规则和控制 API 响应内容所需的配置和自定义。 基于控制器的 API 有一些功能还没有被最小 API 所支持或实现。 其中包括:
- 不提供对模型绑定的内置支持(IModelBinderProvider、IModelBinder)。 可以使用自定义绑定填充码添加支持。
- 不支持从窗体进行绑定。 这包括绑定 IFormFile。
- 不提供对验证的内置支持 (IModelValidator)。
- 不支持应用程序部件或应用程序模型。 无法应用或生成自己的约定。
- 没有内置视图呈现支持。 建议使用 Razor Pages 呈现视图。
- 不支持 JsonPatch
- 不支持 OData