Unity with dynamically loaded UserControl

Oct 16, 2012 at 8:51 PM

Following http://msdn.microsoft.com/en-us/library/ff664622%28v=pandp.50%29.aspx, I got Unity successfully working with ASP.NET WebForms and UserControls embedded on a page; however, if the UserControl is dynamically loaded into a PlaceHolder control via the LoadControl method inside the form's Page_Load method, the DI does not seem to work. Is it possible to inject the dependency into dynamically loaded UserControl? Thanks.

Oct 17, 2012 at 12:49 AM

Which technique from the article are you using?  For your scenario the Basic Approach does not quite cut it -- you should use the recommended approach with an HttpModule.  

ASP.NET Page Life Cycle Overview recommends creating or re-creating dynamic controls in PreInit.  However, if you are using master pages the controls will not be loaded so you can do it in Init (or another workaround is to access the master page in PreInit.  E.g. MasterPage master = this.Master;).

Once the control is added to the PlaceHolder (even though it was dynamically added) it will appear in the ControlCollection and a BuildUp can be performed by the HttpModule to inject any dependencies.

Randy Levy
Enterprise Library support engineer

Oct 17, 2012 at 4:40 AM

I was using the recommended technique. Moving the dynamic control loading to either PreInit or Init works. That peculiar MasterPage statement in PreInit also helps. I really appreciate your suggestions. Thank you very much.

Nov 10, 2012 at 4:21 PM
Edited Nov 10, 2012 at 4:22 PM

The C# example works fine, but there's a bug in the VB.NET version of the GetControlTree method in ASP.NET Dependency Injection HTTP Module. The second loop iterates over the child's controls, yet mistakenly checks and adds the child itself to the controlList, not the child's control being iterated. It took me several days to find out. It should be:

' Get the controls in the page's control tree excluding the page itself
    Private Function GetControlTree(ByVal root As Control) As IEnumerable(Of Control)
      Dim controlList As New List(Of Control)
      For Each child As Control In root.Controls
        If child Is Nothing Then
          Exit For
        End If
        For Each c As Control In GetControlTree(child)
          If c Is Nothing Then
            Exit For
          End If
      Return controlList
    End Function