Upgrading ASP.NET MVC 3 project to ASP.NET MVC 5 experience

comments

There are many guides how to upgrade your project to ASP.NET MVC 5. Some really useful official guides provide only the changing assembly versions solution. Is it so easy task as it seems? Let's review my experience.

TL;DR

What upgrading to ASP.NET MVC 5 brings to developers?

The good question is why worring about upgrading? For me it is:

  • support for attribute routing
  • support of async/await in your controllers
  • support of ASP.NET Web API side-by-side

As side effect, starting from Visual Studio 2013, IDE will emphasize all MVC 3 code in ASP.NET views as erronous and intellisense will not working correctly. After upgrading to MVC 5 this is not issue anymore, I have correct emphasized code errors only and correct intellisense.

Upgrading binaries

The easiest way to upgrade binaries is to use nuget. You can use Package Manager Dialog or Package Manager Console to install these packages:

Nuget will do it's best to include assembly binding redirect into your web.config files (not only for MVC assemblies but for other assemblies too). If you don't use nuget and have external folder with all third-party libraries in your solution, you can just copy ASP.NET MVC 5 binaries to this external folder and have to correct paths in your *.csproj files to new location manually.

Next step is to change namespaces in using statements:

  • Microsoft.Web.Mvc --> System.Web.Mvc
  • Microsoft.Web.Mvc.Html --> System.Web.Mvc.Html

Missing things

There was ASP.NET MVC 3 Futures assembly which is not supported anymore. Our project depended on a few features from it:

  • AjaxOnlyAttribute (there is simple implementation of this attribute)
  • MvcButtonBuilder.SubmitButton (you can use another implementation with the same semantics)
  • We used Microsoft.Web.Mvc.ViewExtensions.RenderAction(this HtmlHelper, Action<T>); and Microsoft.Web.Mvc.LinkExtensions.BuildUrlFromExpression(this HtmlHelper, Action<T>) extension methods in a few places for rendering URLs. We decided to use Html.Action() and Url.Action() methods without expressions as workaround.

Breaking changes in JsonValueProviderFactory class

In MVC 5 the breaking changes was introduced in how json payload fills NameValueCollection for model binding:

  • More strict check for duplicates. Model binding was always case insensitive. JsonValueProviderFactory class implementation in MVC 3 was tolerant to duplicated JSON keys if you POST this JSON:

    {
        "Something": "value 1",
        "someThing": "value 2"
    }
    

    MVC 5 has more strict check and will throw exception in this case. The right way is to ensure that you don't POST JSON with duplicated keys.

  • Upper bounded count of JSON keys to process. In MVC 3 it was possible to hang your web application by posting very large JSON. MVC 5 now checks maximum count of keys in JSON. The default constraint is 1000 keys. And you can change this value using appSettings configuration section in your web.config:

    <appSettings>
        <add key="aspnet:MaxJsonDeserializerMembers" value="268435455" />
    </appSettings>
    

Summary

Upgrading to MVC 5 is almost as easy as updating binaries and make assembly binding redirects. MVC 5 has some breaking changes which have simple workarounds.

Happy upgrading!

Comments