无法在没有 StructureMap 的情况下使用 MediatR 解决 Fluent Validation
Unable to resolve Fluent Validation using MediatR without StructureMap
尝试使用 MediatR 在 .Net Core 3.1 微服务中注入 Fluent Validation 没有结构图。
在 Nuget 包下面添加:
<PackageReference Include="FluentValidation.AspNetCore" Version="8.6.2" />
<PackageReference Include="MediatR" Version="4.0.1" />
<PackageReference Include="MediatR.Extensions.Microsoft.DependencyInjection" Version="4.0.0" />
Startup.cs:
services.AddMvc(options =>
{
options.Filters.Add(typeof(HttpGlobalExceptionFilter));
options.EnableEndpointRouting = false;
}).AddControllersAsServices()
.AddNewtonsoftJson()
.AddViewLocalization(
LanguageViewLocationExpanderFormat.Suffix,
opts => { opts.ResourcesPath = "Resources"; })
.AddDataAnnotationsLocalization()
.SetCompatibilityVersion(CompatibilityVersion.Version_3_0)
.AddFluentValidation(fv=> fv.RegisterValidatorsFromAssemblyContaining(typeof(Startup)));
已注册 IPipelineBehavior 和验证器:
services.AddMediatR();
services.AddTransient(typeof(IPipelineBehavior<,>), typeof(ValidatorBehaviour<,>));
ValidatorBehaviour.cs:
public class ValidatorBehaviour<TRequest, TResponse> : IPipelineBehavior<TRequest, TResponse>
{
private readonly IValidator<TRequest>[] _validators;
public ValidatorBehaviour(IValidator<TRequest>[] validators) => _validators = validators;
public async Task<TResponse> Handle(TRequest request, CancellationToken cancellationToken, RequestHandlerDelegate<TResponse> next)
{
var failures = _validators
.Select(v => v.Validate(request))
.SelectMany(result => result.Errors)
.Where(error => error != null)
.ToList();
if (failures.Any())
{
var errorFieldsMessages = failures.Select(x => x.ErrorMessage + ", ").ToArray();
throw new PomDetailsException(
$"Command Validation Errors for type {typeof(TRequest).Name}. " +
$"Validation failed : {string.Join(string.Empty, errorFieldsMessages)}", new ValidationException("Validation exception", failures));
}
var response = await next();
return response;
}
}
异常:
Unable to resolve service for type 'FluentValidation.IValidator`1[][]' while attempting to activate
我猜我的配置有误,但我已经多次更改配置但没有成功。
任何指导将不胜感激
您正在尝试解析 IValidator<TRequest>
的集合,因此您将构造函数参数指定为 IValidator<TRequest>[]
(数组)。但是框架的 DI 需要为此目的使用 IEnumerable
。如下更新 ValidatorBehaviour
构造函数,它将按预期工作
private readonly IEnumerable<IValidator<TRequest>> _validators;
public ValidatorBehaviour(IEnumerable<IValidator<TRequest>> validators) => _validators = validators;
尝试使用 MediatR 在 .Net Core 3.1 微服务中注入 Fluent Validation 没有结构图。
在 Nuget 包下面添加:
<PackageReference Include="FluentValidation.AspNetCore" Version="8.6.2" />
<PackageReference Include="MediatR" Version="4.0.1" />
<PackageReference Include="MediatR.Extensions.Microsoft.DependencyInjection" Version="4.0.0" />
Startup.cs:
services.AddMvc(options =>
{
options.Filters.Add(typeof(HttpGlobalExceptionFilter));
options.EnableEndpointRouting = false;
}).AddControllersAsServices()
.AddNewtonsoftJson()
.AddViewLocalization(
LanguageViewLocationExpanderFormat.Suffix,
opts => { opts.ResourcesPath = "Resources"; })
.AddDataAnnotationsLocalization()
.SetCompatibilityVersion(CompatibilityVersion.Version_3_0)
.AddFluentValidation(fv=> fv.RegisterValidatorsFromAssemblyContaining(typeof(Startup)));
已注册 IPipelineBehavior 和验证器:
services.AddMediatR();
services.AddTransient(typeof(IPipelineBehavior<,>), typeof(ValidatorBehaviour<,>));
ValidatorBehaviour.cs:
public class ValidatorBehaviour<TRequest, TResponse> : IPipelineBehavior<TRequest, TResponse>
{
private readonly IValidator<TRequest>[] _validators;
public ValidatorBehaviour(IValidator<TRequest>[] validators) => _validators = validators;
public async Task<TResponse> Handle(TRequest request, CancellationToken cancellationToken, RequestHandlerDelegate<TResponse> next)
{
var failures = _validators
.Select(v => v.Validate(request))
.SelectMany(result => result.Errors)
.Where(error => error != null)
.ToList();
if (failures.Any())
{
var errorFieldsMessages = failures.Select(x => x.ErrorMessage + ", ").ToArray();
throw new PomDetailsException(
$"Command Validation Errors for type {typeof(TRequest).Name}. " +
$"Validation failed : {string.Join(string.Empty, errorFieldsMessages)}", new ValidationException("Validation exception", failures));
}
var response = await next();
return response;
}
}
异常:
Unable to resolve service for type 'FluentValidation.IValidator`1[][]' while attempting to activate
我猜我的配置有误,但我已经多次更改配置但没有成功。
任何指导将不胜感激
您正在尝试解析 IValidator<TRequest>
的集合,因此您将构造函数参数指定为 IValidator<TRequest>[]
(数组)。但是框架的 DI 需要为此目的使用 IEnumerable
。如下更新 ValidatorBehaviour
构造函数,它将按预期工作
private readonly IEnumerable<IValidator<TRequest>> _validators;
public ValidatorBehaviour(IEnumerable<IValidator<TRequest>> validators) => _validators = validators;