How to receive a HttpRequest into an MVC 3 controller action?

12,823

You already have a Request property on your controller => you don't need to pass it as action argument.

[HttpPost]
public ActionResult Upload()
{
    var length = Request.ContentLength;
    var bytes = new byte[length];

    if (Request.Files != null)
    {
        if (Request.Files.Count > 0)
        {
            var successJson1 = new { success = true };
            return Json(successJson1);
        }
    }

    return Json(failJson1);
}

Now you can mock the Request in your unit test and more specifically the HttpContext which has a Request property:

// arrange
var sut = new SomeController();
HttpContextBase httpContextMock = ... mock the HttpContext and more specifically the Request property which is used in the controller action
ControllerContext controllerContext = new ControllerContext(httpContextMock, new RouteData(), sut);
sut.ControllerContext = controllerContext;

// act
var actual = sut.Upload();

// assert
... assert that actual is JsonResult and that it contains the expected Data
Share:
12,823
Sean
Author by

Sean

Working in C# - Answering and asking questions to improve my knowledge on c#. Currently trying f#. Expect stupid questions.

Updated on June 12, 2022

Comments

  • Sean
    Sean almost 2 years

    Current Solution

    So I have something very similar to

    [HttpPost]
        public ActionResult Upload()
        {
            var length = Request.ContentLength;
            var bytes = new byte[length];
    
            if (Request.Files != null )
            {
                if (Request.Files.Count > 0)
                {
                    var successJson1 = new {success = true};
                    return Json(successJson1, "text/html");
                }
            }
    ...
            return Json(successJson2,"text/html");
        }
    

    Unit testable solution?

    I want something like this:

    [HttpPost]
    public ActionResult Upload(HttpRequestBase request)
    {
        var length = request.ContentLength;
        var bytes = new byte[length];
    
        if (request.Files != null )
        {
            if (request.Files.Count > 0)
            {
                var successJson1 = new {success = true};
                return Json(successJson1);
            }
        }
    
        return Json(failJson1);
    }
    

    However this fails, which is annoying as I could make a Mock from the base class and use it.

    Notes

    • I am aware this is not a good way to parse a form/upload and would like to say other things are going on here (namely that this upload can be a form or an xmlhttprequest - the action does not know which).
    • Other ways to make "Request" unit testable would also be awesome.