How to mock an ActionExecutingContext with Moq?

I am trying to test the following filter:

using Microsoft.AspNet.Mvc; using Microsoft.AspNet.Mvc.Filters; namespace Hello { public class ValidationFilter : ActionFilterAttribute { public override void OnActionExecuting(ActionExecutingContext filterContext) { if (!filterContext.ModelState.IsValid) { filterContext.Result = new BadRequestObjectResult(filterContext.ModelState); } } } } 

I am trying to make fun of ActionFilterAttribute using Moq.

I am using Mvc 6.0.0-rc1

My first attempt:

 var context = new ActionExecutingContext( new ActionContext(Mock.Of<HttpContext>(), new RouteData(), new ActionDescriptor()), new IFilterMetadata[] { filter, }, new Dictionary<string, object>(), controller: new object()); 

But I could not override ModelState. It looks read-only: https://github.com/aspnet/Mvc/blob/6.0.0-rc1/src/Microsoft.AspNet.Mvc.Abstractions/ActionContext.cs#L25

Then I tried:

 var contextMock = new Mock<ActionExecutingContext>( new ActionContext(Mock.Of<HttpContext>(), new RouteData(), new ActionDescriptor()), new IFilterMetadata[] { filter, }, new Dictionary<string, object>()); 

But when I call filter.OnActionExecuting(contextMock.Object) , I get the following error:

 Castle.DynamicProxy.InvalidProxyConstructorArgumentsException : Can not instantiate proxy of class: Microsoft.AspNet.Mvc.Filters.ActionExecutingContext. Could not find a constructor that would match given arguments: Microsoft.AspNet.Mvc.ActionContext Microsoft.AspNet.Mvc.Filters.IFilterMetadata[] System.Collections.Generic.Dictionary`2[System.String,System.Object] 

How to check a filter that uses ModelState?

+7
unit-testing asp.net-mvc moq xunit
source share
1 answer

I just stumbled upon the same problem and solved it that way.

 [Fact] public void ValidateModelAttributes_SetsResultToBadRequest_IfModelIsInvalid() { var validationFilter = new ValidationFilter(); var modelState = new ModelStateDictionary(); modelState.AddModelError("name", "invalid"); var actionContext = new ActionContext( new Mock<HttpContext>().Object, new Mock<RouteData>().Object, new Mock<ActionDescriptor>().Object, modelState ); var actionExecutingContext = new ActionExecutingContext( actionContext, new List<IFilterMetadata>(), new Dictionary<string, object>(), new Mock<Controller>().Object ); validatationFilter.OnActionExecuting(actionExecutingContext); Assert.IsType<BadRequestObjectResult>(actionExecutingContext.Result); } 
+10
source share

All Articles