Une collection de bibliothèques d'aides pour des projets API minimaux.
Une bibliothèque qui fournit des aides de routage pour un minimum de projets d'API pour l'enregistrement automatique des points de terminaison à l'aide de la réflexion.
La bibliothèque est disponible sur Nuget. Recherchez simplement MinimalHelpers.Routing dans l' interface graphique du gestionnaire de package ou exécutez la commande suivante dans la CLI .NET :
dotnet add package MinimalHelpers.Routing Créez une classe pour maintenir votre inscription à votre manutentionnaire et la faire implémenter l'interface IEndpointRouteHandlerBuilder :
public class PeopleEndpoints : MinimalHelpers . Routing . IEndpointRouteHandlerBuilder
{
public static void MapEndpoints ( IEndpointRouteBuilder endpoints )
{
endpoints . MapGet ( "/api/people" , GetList ) ;
endpoints . MapGet ( "/api/people/{id:guid}" , Get ) ;
endpoints . MapPost ( "/api/people" , Insert ) ;
endpoints . MapPut ( "/api/people/{id:guid}" , Update ) ;
endpoints . MapDelete ( "/api/people/{id:guid}" , Delete ) ;
}
// ...
} Appelez la méthode d'extension MapEndpoints() sur l'objet Webapplication Web dans Program.cs avant l'invocation de la méthode Run() :
// using MinimalHelpers.Routing;
app . MapEndpoints ( ) ;
app . Run ( ) ; Par défaut, MapEndpoints() analysera l'assemblage d'appels pour rechercher des classes qui implémentent l'interface IEndpointRouteHandlerBuilder . Si vos gestionnaires de routes sont définis dans une autre assemblée, vous avez deux alternatives:
MapEndpoints() qui prend l'assemblage pour scanner comme argumentMapEndpointsFromAssemblyContaining<T>() et spécifiez un type contenu dans l'assemblage que vous souhaitez scanner Vous pouvez également décider explicitement de quels types (parmi ceux qui implémentent l'interface IRouteEndpointHandlerBuilder ) que vous souhaitez réellement cartographier, transmettant un prédicat à la méthode MapEndpoints :
app . MapEndpoints ( type =>
{
if ( type . Name . StartsWith ( "Products" ) )
{
return false ;
}
return true ;
} ) ;Remarque Ces méthodes reposent sur la réflexion pour scanner l'assemblage et trouver les classes qui implémentent l'interface
IEndpointRouteHandlerBuilder. Cela peut avoir un impact sur les performances, en particulier dans les grands projets. Si vous avez des problèmes de performances, envisagez d'utiliser la méthode d'enregistrement explicite. De plus, cette solution est incompatibilée avec l'AOT natif.
Une bibliothèque qui fournit un générateur source pour l'enregistrement automatique des points de terminaison dans des projets API minimaux.
La bibliothèque est disponible sur Nuget. Recherchez simplement MinimalHelpers.Routing dans l' interface graphique du gestionnaire de package ou exécutez la commande suivante dans la CLI .NET :
dotnet add package MinimalHelpers.Routing.Analyzers Créez une classe pour maintenir votre inscription à votre manutentionnaire et la faire implémenter l'interface IEndpointRouteHandlerBuilder :
public class PeopleEndpoints : IEndpointRouteHandlerBuilder
{
public static void MapEndpoints ( IEndpointRouteBuilder endpoints )
{
endpoints . MapGet ( "/api/people" , GetList ) ;
endpoints . MapGet ( "/api/people/{id:guid}" , Get ) ;
endpoints . MapPost ( "/api/people" , Insert ) ;
endpoints . MapPut ( "/api/people/{id:guid}" , Update ) ;
endpoints . MapDelete ( "/api/people/{id:guid}" , Delete ) ;
}
// ...
}Remarque Vous n'avez qu'à utiliser le package minimalhelpers.routing.analysers . Avec ce générateur source, l'interface
IEndpointRouteHandlerBuilderest générée automatiquement.
Appelez la méthode d'extension MapEndpoints() sur l'objet Webapplication Web dans Program.cs avant l'invocation de la méthode Run() :
app . MapEndpoints ( ) ;
app . Run ( ) ;Remarque La méthode
MapEndpointsest générée par le générateur source.
Une bibliothèque qui fournit des aides OpenAPI pour un minimum de projets d'API.
La bibliothèque est disponible sur Nuget. Recherchez simplement minimalhelpers.openapi dans l' interface graphique du gestionnaire de package ou exécutez la commande suivante dans la CLI .NET :
dotnet add package MinimalHelpers.OpenApiMéthodes d'extension pour OpenAPI
Cette bibliothèque fournit quelques méthodes d'extensions qui simplifient la configuration OpenAPI dans des projets API minimaux. Par exemple, il est possible de personnaliser la description d'une réponse en utilisant son code d'état:
endpoints . MapPost ( "login" , LoginAsync )
. AllowAnonymous ( )
. WithValidation < LoginRequest > ( )
. Produces < LoginResponse > ( StatusCodes . Status200OK )
. Produces < LoginResponse > ( StatusCodes . Status206PartialContent )
. Produces ( StatusCodes . Status403Forbidden )
. ProducesValidationProblem ( )
. WithOpenApi ( operation =>
{
operation . Summary = "Performs the login of a user" ;
operation . Response ( StatusCodes . Status200OK ) . Description = "Login successful" ;
operation . Response ( StatusCodes . Status206PartialContent ) . Description = "The user is logged in, but the password has expired and must be changed" ;
operation . Response ( StatusCodes . Status400BadRequest ) . Description = "Incorrect username and/or password" ;
operation . Response ( StatusCodes . Status403Forbidden ) . Description = "The user was blocked due to too many failed logins" ;
return operation ;
} ) ;Méthodes d'extension pour RouteHandlerBuilder
Souvent, nous avons des points de terminaison avec plusieurs valeurs de retour 4xx, chacune qui produit une réponse ProblemDetails :
endpoints . MapGet ( "/api/people/{id:guid}" , Get )
. ProducesProblem ( StatusCodes . Status400BadRequest )
. ProducesProblem ( StatusCodes . Status401Unauthorized )
. ProducesProblem ( StatusCodes . Status403Forbidden )
. ProducesProblem ( StatusCodes . Status404NotFound ) ; Pour éviter plusieurs appels à ProducesProblem , nous pouvons utiliser la méthode d'extension ProducesDefaultProblem fournie par la bibliothèque:
endpoints . MapGet ( "/api/people/{id:guid}" , Get )
. ProducesDefaultProblem ( StatusCodes . Status400BadRequest , StatusCodes . Status401Unauthorized ,
StatusCodes . Status403Forbidden , StatusCodes . Status404NotFound ) ; Une bibliothèque qui fournit un filtre de point de terminaison pour un minimum de projets d'API pour effectuer la validation avec des annotations de données, en utilisant la bibliothèque Minivalidation.
La bibliothèque est disponible sur Nuget. Recherchez simplement MinimalHelpers.Validation dans l' interface graphique du gestionnaire de package ou exécutez la commande suivante dans le CLI .NET :
dotnet add package MinimalHelpers.ValidationDécorer une classe avec des attributs pour définir les règles de validation:
using System . ComponentModel . DataAnnotations ;
public class Person
{
[ Required ]
[ MaxLength ( 20 ) ]
public string ? FirstName { get ; set ; }
[ Required ]
[ MaxLength ( 20 ) ]
public string ? LastName { get ; set ; }
[ MaxLength ( 50 ) ]
public string ? City { get ; set ; }
} Ajoutez la méthode d'extension WithValidation<T>() pour activer le filtre de validation:
using MinimalHelpers . Validation ;
app . MapPost ( "/api/people" , ( Person person ) =>
{
// ...
} )
. WithValidation < Person > ( ) ; Si la validation échoue, la réponse sera une 400 Bad Request avec un objet ValidationProblemDetails contenant les erreurs de validation, par exemple:
{
"type" : " https://tools.ietf.org/html/rfc9110#section-15.5.1 " ,
"title" : " One or more validation errors occurred " ,
"status" : 400 ,
"instance" : " /api/people " ,
"traceId" : " 00-009c0162ba678cae2ee391815dbbb59d-0a3a5b0c16d053e6-00 " ,
"errors" : {
"FirstName" : [
" The field FirstName must be a string or array type with a maximum length of '20'. "
],
"LastName" : [
" The LastName field is required. "
]
}
} Si vous souhaitez personnaliser la validation, vous pouvez utiliser la méthode d'extension ConfigureValidation :
using MinimalHelpers . Validation ;
builder . Services . ConfigureValidation ( options =>
{
// If you want to get errors as a list instead of a dictionary.
options . ErrorResponseFormat = ErrorResponseFormat . List ;
// The default is "One or more validation errors occurred"
options . ValidationErrorTitleMessageFactory =
( context , errors ) => $ "There was { errors . Values . Sum ( v => v . Length ) } error(s)" ;
} ) ; Vous pouvez utiliser ValidationErrorTitleMessageFactory , par exemple, si vous souhaitez localiser la propriété title de la réponse à l'aide d'un fichier RESX.
Une bibliothèque qui fournit un filtre de point final pour un minimum de projets d'API pour effectuer la validation à l'aide de FluentValidation.
La bibliothèque est disponible sur Nuget. Recherchez simplement minimalhelpers.fluentvalidation dans l' interface graphique du gestionnaire de package ou exécutez la commande suivante dans la CLI .NET :
dotnet add package MinimalHelpers.FluentValidationCréez une classe qui étend AbstractValidator et définissez les règles de validation:
using FluentValidation ;
public record class Product ( string Name , string Description , double UnitPrice ) ;
public class ProductValidator : AbstractValidator < Product >
{
public ProductValidator ( )
{
RuleFor ( p => p . Name ) . NotEmpty ( ) . MaximumLength ( 50 ) . EmailAddress ( ) ;
RuleFor ( p => p . Description ) . MaximumLength ( 500 ) ;
RuleFor ( p => p . UnitPrice ) . GreaterThan ( 0 ) ;
}
}Enregistrer les validateurs dans la collection de services:
using FluentValidation ;
// Assuming the validators are in the same assembly as the Program class
builder . Services . AddValidatorsFromAssemblyContaining < Program > ( ) ; Ajoutez la méthode d'extension WithValidation<T>() pour activer le filtre de validation:
using MinimalHelpers . FluentValidation ;
app . MapPost ( "/api/products" , ( Product product ) =>
{
// ...
} )
. WithValidation < Product > ( ) ; Si la validation échoue, la réponse sera une 400 Bad Request avec un objet ValidationProblemDetails contenant les erreurs de validation, par exemple:
{
"type" : " https://tools.ietf.org/html/rfc9110#section-15.5.1 " ,
"title" : " One or more validation errors occurred " ,
"status" : 400 ,
"instance" : " /api/products " ,
"traceId" : " 00-f4ced0ae470424dd04cbcebe5f232dc5-bbdcc59f310ebfb8-00 " ,
"errors" : {
"Name" : [
" 'Name' cannot be empty. "
],
"UnitPrice" : [
" 'Unit Price' must be grater than '0'. "
]
}
} Si vous souhaitez personnaliser la validation, vous pouvez utiliser la méthode d'extension ConfigureValidation :
using MinimalHelpers . Validation ;
builder . Services . ConfigureValidation ( options =>
{
// If you want to get errors as a list instead of a dictionary.
options . ErrorResponseFormat = ErrorResponseFormat . List ;
// The default is "One or more validation errors occurred"
options . ValidationErrorTitleMessageFactory =
( context , errors ) => $ "There was { errors . Values . Sum ( v => v . Length ) } error(s)" ;
} ) ; Vous pouvez utiliser ValidationErrorTitleMessageFactory , par exemple, si vous souhaitez localiser la propriété title de la réponse à l'aide d'un fichier RESX.
Contribuer
Le projet évolue constamment. Les contributions sont les bienvenues. N'hésitez pas à déposer des problèmes et à réaliser des demandes sur le dépôt et nous les résoudrons comme nous le pouvons.