ObjectBuilder Can Inject to UserControls As Well

October 5, 2007 - 2 minute read -
ObjectBuilder asp.net dependency injection csharp

This is a followup to my previous post on integrating ObjectBuilder and ASP.NET. As I was playing around with the solution I hit on the fact that I was only injecting at the Page level. As ASP.NET is a component model, you can end up with custom User Controls that would need injected properties as well. There is a relatively simple, if not entirely obvious way to do that as well.

Building on the previous example, you can hook into the lifecycle of a page that you are injecting. You can not access the controls directly in the PreRequestHandlerExecute of the IHttpModule because they have not been instantiated yet. Instead, you can create a callback event handler for the Page.InitComplete event and inject properties at that point.

void InjectProperties(object sender, EventArgs e)
{
    IHttpHandler h = app.Context.CurrentHandler;
    if (h is DefaultHttpHandler)
        return;
    chain.Head.BuildUp(builderContext, h.GetType(), h, null);
    if (h is Page)
    {
        // Register a page lifecycle event handler to inject
        // user controls on the page itself
        page = (Page) h;
        page.InitComplete += InjectControls;
    }
}</p>
<p>private void InjectControls(object sender, EventArgs e)
{
    InjectControls(page);
    if (null != page.Form)
        InjectControls(page.Form);
}</p>
<p>private void InjectControls(Control mainControl)
{
    if (mainControl.Controls != null && mainControl.Controls.Count > 0)
    {
        foreach (Control c in mainControl.Controls)
        {
            if (c is UserControl)
            {
                chain.Head.BuildUp(builderContext, c.GetType(), c, null);
                InjectControls(c);
            }
        }
    }
}

As you see with this example, you need to recursively inject the objects into all of the controls. That's in case there are any nested controls that might need injecting. The other thing to notice is that the controls in the top-level Page doe not contain all of the controls that are also declared in a Form on the page, so you need to handle both of those paths.

Hopefully this will get you further along the path to being able to do dependency injection in your ASP.NET application.