Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

The PipelineBehavior is failing because of a List property in IRequest? #317

Closed
coderabsolute opened this issue Oct 2, 2018 · 6 comments

Comments

@coderabsolute
Copy link

coderabsolute commented Oct 2, 2018

Am getting the following error when I use the PipelineBehavior only when a List is used as a property. Not sure whether the IPipelineBehavior is not handling the List or something am doing incorrectly? When I remove the List property then the code gets executed. Maybe, am doing something wrong, can someone please help me. Thanks in advance!

fail: Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddleware[1]
      An unhandled exception has occurred while executing the request.
System.NullReferenceException: Object reference not set to an instance of an object.
   at MediatR.Internal.RequestHandlerWrapperImpl`2.<>c__DisplayClass0_1.<Handle>b__2()
   at MediatR.Internal.RequestHandlerWrapperImpl`2.Handle(IRequest`1 request, CancellationToken cancellationToken, ServiceFactory serviceFactory)
   at MediatR.Mediator.Send[TResponse](IRequest`1 request, CancellationToken cancellationToken)
   at Api.Controllers.CustomersController.Post(CustomerAddRequest model) in \Controllers\CustomersController.cs:line 23
   at Microsoft.AspNetCore.Mvc.Internal.ActionMethodExecutor.TaskOfIActionResultExecutor.Execute(IActionResultTypeMapper mapper, ObjectMethodExecutor executor, Object controller, Object[] arguments)
   at System.Threading.Tasks.ValueTask`1.get_Result()
   at Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker.InvokeActionMethodAsync()
   at Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker.InvokeNextActionFilterAsync()
   at Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker.Rethrow(ActionExecutedContext context)
   at Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker.Next(State& next, Scope& scope, Object& state, Boolean& isCompleted)
   at Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker.InvokeInnerFilterAsync()
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.InvokeNextExceptionFilterAsync()
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.Rethrow(ExceptionContext context)
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.Next(State& next, Scope& scope, Object& state, Boolean& isCompleted)
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.InvokeNextResourceFilter()
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.Rethrow(ResourceExecutedContext context)
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.Next(State& next, Scope& scope, Object& state, Boolean& isCompleted)
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.InvokeFilterPipelineAsync()
   at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.InvokeAsync()
   at Microsoft.AspNetCore.Builder.RouterMiddleware.Invoke(HttpContext httpContext)
   at Microsoft.AspNetCore.StaticFiles.StaticFileMiddleware.Invoke(HttpContext context)
   at Swashbuckle.AspNetCore.SwaggerUI.SwaggerUIIndexMiddleware.Invoke(HttpContext httpContext)
   at Swashbuckle.AspNetCore.Swagger.SwaggerMiddleware.Invoke(HttpContext httpContext)
   at Microsoft.AspNetCore.Authentication.AuthenticationMiddleware.Invoke(HttpContext context)
   at Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddleware.Invoke(HttpContext context)

Here is the actual code am executing.

public class CustomerAddRequest : IRequest<CommandResponse>
{
	public string CustomerName { get; set; }
	public string CustomerCode { get; set; }
	public string RegistrationNumber { get; set; }
	public string ShortName { get; set; }
	public double CreditLimit { get; set; }
	public IEnumerable<AddressAddRequest> Addresses { get; set; }
}

public class AddressAddRequest
{
	public int AddressTypeId { get; set; }

	public string Address1 { get; set; }
	public string Address2 { get; set; }
	public string Address3 { get; set; }
	public string City { get; set; }
	public string State { get; set; }
	public int CountryId { get; set; }
	public string ZipCode { get; set; }
}


public class CustomerAddPipelineBehavior<TRequest, TResponse> : IPipelineBehavior<TRequest, TResponse>
	where TRequest : CustomerAddRequest
	where TResponse : CommandResponse
{
	public async Task<TResponse> Handle(TRequest request, CancellationToken cancellationToken, RequestHandlerDelegate<TResponse> next)
	{
		return await next();
	}
}

The Addresses property in the AddressAddRequest class is causing the issue. If I remove this property all works well. Any guess please? :)

public IEnumerable<AddressAddRequest> Addresses { get; set; }

This is how am registering with the ServiceCollection.

services.AddScoped(typeof(IPipelineBehavior<,>), typeof(CustomerAddPipelineBehavior<,>));

@coderabsolute
Copy link
Author

Looks like the problem is something else, I have a problem registering multiple classes for IPipelineBehavior using ASP.NET DI. I will do a search on google to find out more.

@coderabsolute
Copy link
Author

coderabsolute commented Oct 3, 2018

I resolved by passing in the Classes like this. Is there a better way to handle this? If not, I will close this issue.

services.AddScoped(typeof(IPipelineBehavior<CustomerAddRequest, CommandResponse>), typeof(CustomerAddBehavior<CustomerAddRequest, CommandResponse>));
services.AddScoped(typeof(IPipelineBehavior<BrandDeleteRequest, CommandResponse>), typeof(BrandDeleteBehavior<BrandDeleteRequest, CommandResponse>));
services.AddScoped(typeof(IPipelineBehavior<CustomerDeleteRequest, CommandResponse>), typeof(CustomerDeleteBehavior<CustomerDeleteRequest, CommandResponse>));

@jbogard
Copy link
Owner

jbogard commented Oct 3, 2018 via email

@coderabsolute
Copy link
Author

coderabsolute commented Oct 3, 2018

These my original registrations which didn't resolve by itself. Maybe, am missing out something?

services.AddScoped(typeof(IPipelineBehavior<,>), typeof(CustomerAddBehavior<,>));
services.AddScoped(typeof(IPipelineBehavior<,>), typeof(BrandDeleteBehavior<,>));
services.AddScoped(typeof(IPipelineBehavior<,>), typeof(CustomerDeleteBehavior<,>));

@jbogard
Copy link
Owner

jbogard commented Oct 3, 2018

Ah. You can't do generic type constraints with vanilla MS.Extensions.DI. See my PR to fix this:

aspnet/DependencyInjection#635

@jbogard
Copy link
Owner

jbogard commented Oct 3, 2018

If you want generic constraints, you have to pull in an 3rd-party container.

@jbogard jbogard closed this as completed Oct 3, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants