У меня есть следующий обработчик, который я использую, пытаясь прикрепить поведение к любому IRequest
, который также реализует IRetryOnConflict
.
public class RetryOnConcurrencyRequestHandlerDecorator<TRequest, TResponse> : IRequestHandler<TRequest, TResponse>
where TRequest : IRequest<TResponse>, IRetryOnConflict
{
private readonly IConcurrencyRetryPolicy retryPolicy;
private readonly IRequestHandler<TRequest, TResponse> innerHandler;
public RetryOnConcurrencyRequestHandlerDecorator(IRequestHandler<TRequest, TResponse> innerHandler, IConcurrencyRetryPolicy retryPolicy)
{
this.innerHandler = innerHandler;
this.retryPolicy = retryPolicy;
}
public Task<TResponse> Handle(TRequest request, CancellationToken cancellationToken)
{
return retryPolicy.Execute(() => innerHandler.Handle(request, cancellationToken));
}
}
А вот мой регистрационный код, который запускается при запуске:
container.Register(typeof(IRequestHandler<,>), typeof(RetryOnConcurrencyRequestHandlerDecorator<,>), setup: Setup.Decorator);
Я просматривал некоторые из наших файлов журналов и вижу следующие ошибки:
System.TypeLoadException
GenericArguments[0], 'ReadModel.SaleRegistrations.Queries.GetSaleRegistration', on 'Infrastructure.MediatR.RetryOnConcurrencyRequestHandlerDecorator`2[TRequest,TResponse]' violates the constraint of type parameter 'TRequest'.
system.private.corelib!DomainNeutralILStubClass.IL_STUB_PInvoke
system.private.corelib!System.RuntimeTypeHandle.Instantiate
system.private.corelib!System.RuntimeType.MakeGenericType
dryioc!DryIoc.ReflectionFactory+ClosedGenericFactoryGenerator+<>c__DisplayClass3_0.<GetGeneratedFactory>b__0
dryioc!DryIoc.Throw.IfThrows
dryioc!DryIoc.ReflectionFactory+ClosedGenericFactoryGenerator.GetGeneratedFactory
dryioc!DryIoc.Container+<>c__DisplayClass56_0.<DryIoc.IContainer.GetDecoratorExpressionOrDefault>b__4
dryioc!ImTools.ArrayTools.Map
dryioc!DryIoc.Container.DryIoc.IContainer.GetDecoratorExpressionOrDefault
dryioc!DryIoc.Factory.GetExpressionOrDefault
dryioc!DryIoc.Container.ResolveAndCacheFactoryDelegate
dryioc!DryIoc.Container.DryIoc.IResolver.Resolve
dryioc!DryIoc.Resolver.Resolve
mediatr!MediatR.ServiceFactoryExtensions.GetInstance
mediatr!MediatR.Internal.RequestHandlerBase.GetHandler
mediatr!MediatR.Internal.RequestHandlerWrapperImpl`2+<>c__DisplayClass0_0[System.__Canon,System.__Canon].<Handle>g__Handler|0
mediatr!MediatR.Pipeline.RequestPreProcessorBehavior`2+<Handle>d__2[System.__Canon,System.__Canon].MoveNext
System.Private.CoreLib!System.Runtime.CompilerServices.AsyncMethodBuilderCore.Start
System.Private.CoreLib!System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1[System.__Canon].Start
mediatr!MediatR.Pipeline.RequestPreProcessorBehavior`2[System.__Canon,System.__Canon].Handle
mediatr!MediatR.Internal.RequestHandlerWrapperImpl`2+<>c__DisplayClass0_1[System.__Canon,System.__Canon].<Handle>b__2
mediatr!MediatR.Pipeline.RequestPostProcessorBehavior`2+<Handle>d__2[System.__Canon,System.__Canon].MoveNext
System.Private.CoreLib!System.Runtime.CompilerServices.AsyncMethodBuilderCore.Start
System.Private.CoreLib!System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1[System.__Canon].Start
mediatr!MediatR.Pipeline.RequestPostProcessorBehavior`2[System.__Canon,System.__Canon].Handle
mediatr!MediatR.Internal.RequestHandlerWrapperImpl`2+<>c__DisplayClass0_1[System.__Canon,System.__Canon].<Handle>b__2
mediatr!MediatR.Internal.RequestHandlerWrapperImpl`2[System.__Canon,System.__Canon].Handle
mediatr!MediatR.Mediator.Send
functions!Functions.Components.SaleRegistrations.Aggregator.Activities.GetSaleRegistrationActivityController+<Execute>d__2.MoveNext
System.Private.CoreLib!System.Runtime.CompilerServices.AsyncMethodBuilderCore.Start
functions!Functions.Components.SaleRegistrations.Aggregator.Activities.GetSaleRegistrationActivityController.Execute
functions!Functions.Components.SaleRegistrations.Aggregator.Activities.GetSaleRegistrationActivity+<GetSaleRegistration>d__1.MoveNext
System.Private.CoreLib!System.Runtime.CompilerServices.AsyncMethodBuilderCore.Start
functions!Functions.Components.SaleRegistrations.Aggregator.Activities.GetSaleRegistrationActivity.GetSaleRegistration
anonymously hosted dynamicmethods assembly!dynamicClass.lambda_method
microsoft.azure.webjobs.host!
microsoft.azure.webjobs.host!
system.private.corelib!System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1+AsyncStateMachineBox`1+<>c[System.__Canon,System.__Canon].<.cctor>b__9_0
system.private.corelib!System.Threading.ExecutionContext.RunInternal
system.private.corelib!System.Runtime.CompilerServices.AsyncTaskMethodBuilder`1+AsyncStateMachineBox`1[System.__Canon,System.__Canon].MoveNext
system.private.corelib!System.Runtime.CompilerServices.YieldAwaitable+YieldAwaiter+<>c.<OutputCorrelationEtwEvent>b__6_0
system.private.corelib!System.Runtime.CompilerServices.AsyncMethodBuilderCore+ContinuationWrapper.Invoke
system.private.corelib!System.Threading.QueueUserWorkItemCallback.ExecuteWorkItem
system.private.corelib!System.Threading.ThreadPoolWorkQueue.Dispatch
system.private.corelib!System.Threading._ThreadPoolWaitCallback.PerformWaitCallback
По какой-то причине это говорит мне о том, что следующее IRequest
каким-то образом украшаетсяс моим RetryOnConcurrencyRequestHandlerDecorator
, хотя он не реализует IRetryOnConflict
.
public class GetSaleRegistration : IRequest<SaleRegistration>
{
}
Любые идеи о том, где я иду не так?
Спасибо!