ASP.net MVC, MVCContrib, and Using Spring.net as a Controller Factory

The ASP.net MVC CTP as been out for a few days and I have read quite a number of good posts about using the framework and extending the available functionality.  Keep an eye on the MVCContrib project over on CodePlex.  I can already see that many good things are going to come from this project, based on the functionality already being worked on.  There is already integration with the popular Dependency Injection (DI) containers including Windsor, StructureMap, and Spring.net (my contribution to the project).  For fans of Resharper, like myself, there will be some live templates developed to help with the normal programming tasks for ASP.net MVC projects.

For this post, I will be discussing the usage of the SpringControllerFactory and how it integrates with ASP.net MVC.

ASP.net MVC has the concept of a Controller Factory (IControllerFactory) that is used to create controller instances.  Developers can create their own IControllerFactory implementations to take advantage of class factory implementations already in use or DI/IoC containers like Spring.net.  SpringControllerFactory is the IControllerFactory implementation that is included with MVCContrib.  Getting started with using this controller factory is easy.  Below is a repeat of the brief documentation that I created on the MVCContrib Wiki for SpringControllerFactory, with some additional commentary.

First, you will need to add a reference to MVCContrib.Spring.dll to your project.  After adding the reference, you need to add some code to the Global.asax.cs file in your MVC application project to Configure the controller factory and tell the MVC framework about it.

protected void Application_Start(object sender, EventArgs e)
{
    //This example just sets the default context for 
    //use with the Spring.net Controller
    //Factory.  An IObjectFactory instance is also 
    //supported, if greater control over
    //Spring.net is desired.
 
    IApplicationContext ctx = ContextRegistry.GetContext();
    SpringControllerFactory.Configure(ctx);
 
    ControllerBuilder.Current.SetDefaultControllerFactory(
        typeof(SpringControllerFactory));
 
    //more configuration code for the MVC framework
} 

The code above retrieves the default Spring.net context and passes it to the static Configure() method on SpringControllerFactory.  Configure() will accept either an IObjectFactory instance or an IApplicationContext instance. Spring.net documentation recommends the IApplicationContext approach for most cases. IObjectFactory implementations allow for greater flexibility when you need it. This step is necessary to allow the developer to share the Spring.net context with the controller factory and any other components there might be in the application.  In other words, this allows a singleton to really be a singleton for the entire appdomain.  Since currently there is no way to pass an instance of a controller factory to ControllerBuilder (notice that SetDefaultControllerFactory() accepts a Type), somewhat ugly approaches need to be taken to share state between controller factories and other components. 

Some will probably not like the approach I took with the static Configure() method.  I went with the static method approach because I thought it was the most strait forward way of communicating to developers what needs to happen before the controller factory is used.  The developer of the Windsor controller factory implementation for MVCContrib took the approach of requiring the developer to extend the HttpApplication to implement the Windsor IContainerAccessor interface.  I really like this implementation but Spring.net does not really have the equivalent concept so I went with the simple static method approach.

The instances of IController that you create for your application now need to be configured in Spring.net.  Note that the object name for the IController instances need to be the Type.Name of each particular instance.  This isn’t really a great approach either, but like SetDefaultControllerFactory(), IControllerFactory.GetController() only accepts a Type parameter.   Phil Haack said they are looking into possibly changing this.  Phil, can you guys also look into allowing developers to pass an instance of IControllerFactory to the ControllerBuilder as well?  Pretty please?

Below is a shell of an IController implementation that I used for the unit testing of SpringControllerFactory and the configuration that would go along with it.

public class SimpleController : IController
{
    public void Execute(ControllerContext controllerContext)
    {
        //controller code goes here
    }
} 
<objects xmlns="http://www.springframework.net"
                xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                xsi:schemaLocation="http://www.springframework.net http://www.springframework.net/xsd/spring-objects.xsd">
 
  <object id="SimpleController" singleton="true" type="Examples.SimpleController"/>
 
</objects>

I am working on a full working sample application that uses Spring.net for the controller factory.  That sample will be included in the MVCContrib source tree as well and should be there soon.

kick it on DotNetKicks.com

Tags: , , , , , ,

Comments

4 Responses to “ASP.net MVC, MVCContrib, and Using Spring.net as a Controller Factory”

  1. { null != Steve } » Spring.NET and DI with WebForms on March 8th, 2008 8:00 am

    […] Side note: Curious about Spring.NET with MS MVC ?  Here is an approach one programmer has used… […]

  2. lomaxx on July 5th, 2009 7:14 am

    thanks for the SpringControllerFactory. Probably the best thing about DI for controllers is being able to put your controllers in any project you like. Previously being forced to use controllers from within the controller folder was ok for smaller projects, but really quickly became harder to manage for larger projects.

  3. Jet Lee on October 14th, 2009 8:30 pm

    Thank you for you arical…
    I’am a IT developer from China…
    In your arical you said “First, you will need to add a reference to MVCContrib.Spring.dll to your project. “。But I can’t find “MVCContrib.Spring.dll” anywhere…Would you please help me and send a e-mail to me?
    Thank you for you help!

  4. Michael D. Hall on January 5th, 2010 12:57 pm

    @jet This answer comes a little late, but the MvcContrib project has deprecated the IoC containers and no longer supports them. Although it’s easy to add the controller support to you project by copying the source code from the project into your application. Just download the source code from CodePlex and look in the “Deprecated” folder and there should be some sample code for using the Spring controller.