Introduction to using StructureMap for Dependency Injection

StructureMap is an open source tool I’ve written for Dependency Injection support in .Net.  This past week I’ve had a couple requests for a gentle introduction to StructureMap, so here’s my first attempt.  Typically I use StructureMap in a handful of ways:


 



  1. Configuration and creation of services (little “s”) that my code depends upon.  By service here I don’t necessarily mean SOA and web services, but web service proxy classes are an automatic candidate for StructureMap configuration.  I’m referring to subsystems of your application like logging modules, persistence, gateways to other systems, or really anything that you don’t want your code to be tightly coupled to.
  2. Object composition.  Code reuse and unit testing is easier when you favor composition over inheritance relationships, but composition implies that you need to some mechanical coding work just to put the object graph together.  This is where StructureMap comes into play.
  3. Plugin support.  Occasionally there is a real need for pluggable, extensible application frameworks.

 


 


A Contrived Example


 


Let’s say you’re an integration developer in a shop with a crazily mixed bag of applications floating around a big central database.  You want to write a pluggable infrastructure for batch scheduling little integration tasks.  You may need to pull data by a sql query, a stored procedure, or by opening a file – then do something with the data.  All you really know is that the possible sources of the data and the actions on the data will change over time.  You might decide to create a pluggable framework using StructureMap to handle the configuration (Okay, in reality you would probably buy something off of the shelf or utilize DTS out of the box, but I needed an example).


 


First off, let’s ignore the configuration schema and concentrate on defining a set of interfaces and roles for our “Trigger” framework.  The main interface will be this:


 


      public interface ITrigger


      {


            // Do whatever it is that you do


            void Execute();


 


            // Tell me when you want to run next


            DateTime NextExecutionTime();


      }


 


Configuring the most basic trigger class will define the mechanism to retrieve the data, an action to perform on the data, and a strategy for determining the next run time (next Monday, the top of the next hour, the last day of the month, etc.).  That adds the following code:


 


      [Pluggable("Basic")] // Tell StructureMap that it “builds” this class and that it’s alias is “Basic”


      public class Trigger : ITrigger


      {


            private readonly IScheduler _scheduler;


            private readonly IDataSource _source;


            private readonly IAction _action;


 


            public Trigger(IScheduler scheduler, IDataSource source, IAction action)


            {


                  _scheduler = scheduler;


                  _source = source;


                  _action = action;


            }


 


            public void Execute()


            {


                  DataTable table = _source.FetchTable();


                  _action.Process(table);


            }


 


            public DateTime NextExecutionTime()


            {


                  return _scheduler.GetNextRunTime(DateTime.Now);


            }


      }


 


      public interface IDataSource


      {


            DataTable FetchTable();


      }


 


      public interface IAction


      {


            void Process(DataTable table);


      }


 


      public interface IScheduler


      {


            DateTime GetNextRunTime(DateTime currentTime);


      }


 


The first Trigger that we’re going to need to build is going to daily run a SQL query against the central database, and then email the results to an unlucky support person for resolution.  First we create the little classes for the scheduling, data source, and the action.


 


      [Pluggable("SQL")]


      public class SqlDataSource : IDataSource


      {


            private readonly string _sql;


            private readonly IDatabase _database;


 


            public SqlDataSource(IDatabase database, string sql)


            {


                  _sql = sql;


                  _database = database;


            }


 


            public DataTable FetchTable()


            {


                  return _database.FetchDataTable(_sql);


            }


      }


 


      [Pluggable("Email")]


      public class EmailAction : IAction


      {


            public EmailAction(string to, string body){…}


            public void Process(DataTable table){…}


      }


 


      [Pluggable("Daily")]


      public class DailyScheduler : IScheduler


      {


            public DailyScheduler(){}


            public DateTime GetNextRunTime(DateTime currentTime){…}


      }


 


SqlDataSource itself depends upon the IDatabase interface that provides access to an underlying database and handles the raw ADO.Net manipulation.  Let’s say that the central database is a Sql Server database (but I’m starting to miss good old reliable Oracle).  That adds the following to the code:


 


      public interface IDatabase


      {


            DataTable FetchDataTable(string sql);


            void SetStoredProcedureName(string storedProcedureName);


            void SetParameter(string parameterName, object parameterValue);


            DataTable FetchDataTableFromStoredProcedure();


      }


 


      public class SqlDatabase : IDatabase {…}


 


Okay, now we can finally make our StructureMap configuration to create the object graph for our first Trigger.  The first thing we need to do is create a file named “StructureMap.config” that will be copied to the application directory.  At a minimum, we need to define four things for StructureMap:


 



  1. <Assembly> – The .Net assemblies to scan for possible interfaces and classes to be built by StructureMap
  2. <PluginFamily> – The .Net types that can be requested from StructureMap.  In our case this would be the ITrigger, IDataSource, IAction, and IScheduler interfaces.  It can also be abstract or concrete classes as well.
  3. <Plugin> – The concrete .Net types that will implement the interfaces of the PluginFamily types.
  4. <Instance> – The actual object graph configurations.  Notice that we didn’t do anything special in our classes to enable StructureMap (except the [Pluggable] attributes).  All you need to do to enable your class to be configured by StructureMap is to take in all dependencies and properties in a constructor function.  StructureMap also supports “Setter Injection,” but that’s really just meant for Types that aren’t under your control.

 


Jumping into the StructureMap.config file we’ll first configure the default IDatabase instance to point to the central Sql Server database.


 


<?xml version=”1.0″ encoding=”utf-8″ ?>


<StructureMap>


      <!– Tell StructureMap to scan the StructureMapSample.dll assembly for possible PluginFamily’s and Plugin’s –>


      <Assembly Name=”StructureMapSample” />


     


      <!– Define a PluginFamily for IDatabase, making the default instance “CentralDatabase” –>


      <PluginFamily Assembly=”StructureMapSample” Type=”StructureMapSample.IDatabase” DefaultKey=”CentralDatabase”>


            <!– Tell StructureMap that the SqlDatabase class is a plugin to IDatabase called “MicrosoftSqlServer” –>


            <Plugin Assembly=”StructureMapSample” Type=”StructureMapSample.SqlDatabase” ConcreteKey=”MicrosoftSqlServer”/>


           


            <!– Configure the “CentralDatabase” instance of IDatabase.  The <Property> nodes define the arguments to the constructor


            functions –>


            <Instance Key=”CentralDatabase” Type=”MicrosoftSqlServer”>


                  <Property Name=”connectionString” Value=”connection string to somewhere…”/>


            </Instance>


      </PluginFamily>


</StructureMap>


 


With this configuration we could at anytime in our code type IDatabase database = (IDatabase) ObjectFactory.GetInstance(typeof(IDatabase)); to get a configured instance of the SqlDatabase class with the connection string set.  If the database changed to Oracle or DB2 later, only the configuration to create a different concrete IDatabase class would be changed (yeah right).  In this case I defined the Plugin explicitly in the XML configuration.  The [Pluggable(“My Plugin Alias”)] attribute is an equivalent mechanism to using the <Plugin> node.  I prefer the attributes wherever possible, but some people feel differently. 


 


Moving on to the first Trigger instance, we would add a <PluginFamily> node for ITrigger and an <Instance> node for the object graph for the first Trigger.


 


      <PluginFamily Assembly=”StructureMapSample” Type=”StructureMapSample.ITrigger”>


            <!– Create a BasicTrigger object, and give it a DailyScheduler, –>


            <!– Uses the public Trigger(IScheduler scheduler, IDataSource source, IAction action) constructor function –>


            <Instance Type=”Basic” Key=”MyFirstTrigger”>


           


                  <!– DailyScheduler –>


                  <Property Name=”scheduler” Type=”Daily” />


                 


                  <!– SqlDataSource(IDatabase database, string sql) –>


                  <!– By leaving off an explicit definition for “database” StructureMap will use the default


                       “CentralDatabase” instance –>


                  <Property Name=”source” Type=”SQL”>


                        <Property Name=”sql” Value=”select * from errorlog”/>


                  </Property>


                 


                  <!– public EmailAction(string to, string body) –>


                  <Property Name=”action” Type=”Email”>


                        <Property Name=”to” Value=”poorfool@helpdesk.company.com”/>


                        <Property Name=”body” Value=”Fix these now!” />


                  </Property>


            </Instance>


      </PluginFamily>


 


The Trigger framework can now create this instance by calling into StructureMap as something like this:


 


            public void RunTriggers()


            {


                  string[] triggersToRun = this.findTriggersToRun();


 


                  foreach (string triggerName in triggersToRun)


                  {


                        // Ask StructureMap to build the object instance


                        ITrigger trigger =


                              (ITrigger) ObjectFactory.GetNamedInstance(typeof(ITrigger), triggerName);


 


                        trigger.Execute();


                        DateTime nextTime = trigger.NextExecutionTime();


 


                        this.rescheduleTrigger(triggerName, nextTime);


                  }


            }


 


Additional trigger’s could be created by simply configuring the object graphs into the StructureMap.config file as a new <Instance> node.  The big advantage in this case is that StructureMap can quite happily accommodate any new classes that you create later to implement the ITrigger/IDataSource/IAction interfaces.  You could even “plugin” all new assemblies to be used by your application without recompilation.  That’s potentially a huge win for my company because of the sheer number of per client customizations that we have to do.


 


There is far more information and an actual schema document at http://structuremap.sourceforge.net.  I threw this together in a hurry, so please let me know if this is useful or if something else is necessary to make the tool more clear.  Sometime in the near-ish future I’ll post much more on some of the new capabilities for configuration management and environment testing that we’re building into StructureMap for complex build and staging scenarios.

About Jeremy Miller

Jeremy is the Chief Software Architect at Dovetail Software, the coolest ISV in Austin. Jeremy began his IT career writing "Shadow IT" applications to automate his engineering documentation, then wandered into software development because it looked like more fun. Jeremy is the author of the open source StructureMap tool for Dependency Injection with .Net, StoryTeller for supercharged acceptance testing in .Net, and one of the principal developers behind FubuMVC. Jeremy's thoughts on all things software can be found at The Shade Tree Developer at http://codebetter.com/jeremymiller.
This entry was posted in StructureMap. Bookmark the permalink. Follow any comments here with the RSS feed for this post.
  • amita sexana

    Access File Repair
    access password recovery
    Access Password Recovery Software
    MS Access Password Recovery
    Access Password Recovery Tool
    Fix Excel
    download free key logger
    Chat Archive Recovery
    Database conversion software
    MS excel repair software
    Data Recovery Tool
    Web Hosting
    Free Data Wiper
    Digital camera photo recovery software
    Disk Recovery Software
    Data recovery software free download
    Database Converters
    Free Keylogger
    Excel File Recovery
    MS Access Password Recovery Tool
    Excel Recovery
    free keylogger software
    Floppy Recovery
    Repair Excel
    Excel Repair
    recover msn password
    Excel File Fix
    Floppy Disk Recovery
    Windows Data Recovery
    Keystroke Logger
    Hard drive data recovery
    Free Excel Recovery
    Windows Recovery Tools
    IE Password Recovery
    IPod Recovery
    Key logger
    Excel Recovery Tool
    download a free keylogger
    keyloggers free
    keylogger freeware
    Keylogger Spy Software
    keylogger software free
    keystroke capture
    Keylogger
    Recovery Password
    free keylogger downloads
    best keylogger free
    msn password recovery
    Outlook Express Password Recovery Software
    password finder
    Keylogger Software Download
    Password Recovery
    password recovery software
    password recovery software free
    pen drive data recovery software
    Pen Drive Recovery
    PowerPoint Repair Tool
    Chat Recovery Software
    Fix Excel File
    Restore Excel File
    Email Recovery
    cell phone sms recovery software
    recovery for excel
    Repair Excel Files
    repair excel files software
    Data Recovery Software
    sim card deleted sms recovery
    SIM Card Data Recovery
    Key logger software
    downloadable keylogger
    download keylogger freeware
    free invisible keylogger
    data recovery
    Download Free Keylogger
    keystroke recorder
    software keylogger
    remote key logger
    sim recovery
    Sim Card Recovery
    Backlinks Checker Tool
    remote keylogger free
    Spy Keylogger
    USB drive data recovery
    Free Backlink Finder Tool
    datarecovery
    Zip Repair Tool
    keylogger
    Data recovery software for NTFS
    Recovery Format Data
    Partition recovery software
    SEO
    Backlinks Checker
    Sim Card SMS Recovery
    Word file repair software
    data recovery services

    Thanks for this usefull information, i really need it.

  • Victor

    I’m really interested in using StructureMap as my IoC of choice, but haven’t been able to find solid examples. Are there any complete downloadable examples, like the ones MS has for Unity?

  • http://revizyonileorganizematbaacilikbrnckvvtmllttrhaberi.bloggum.com revizyon ile organize matbaacılık brnckvvtmllttrhaberi

    Very Quick and Simple Dependency Injection with StructureMap

  • http://codebetter.com/blogs/jeremy.miller Jeremy D. Miller

    @Cliff,

    Yes, but watch your build procedures. You’ll have to pull that off in the Xml, or create a completely new assembly that references all three of the other assemblies just to hold the STructureMap configuration. One way or another, StructureMap has to be able to load any assembly through the normal mechanisms. You’ll have to copy around the assemblies yourself instead of depending upon VS to do it for you.

  • http://www.graytechnology.com Cliff

    Is it possible to use StructureMap to map types across projects without having a reference? For example, if you have three projects: web (references model), model, and data (references model) can you in the web project set up a mapping from an interface in the Model project to a concrete type in the Data project, without having a project reference to data from web?

  • ms440

    Hi Jeremy,

    I’ve used the StructureMap 1.0 in one of my prev project.

    After watching the screencast that you and Rob Conery put together last week, I realized that I’d like to get back to StructureMap in my new project (not ASP.NET MVC) again. Two questions though:

    First, during the screencast you’ve promised to put together some documentation for 2.5. What’s the ETA for that? Would I be able to use it within my application project timeframe (I’ll have to make a decision about the use of StructureMap before the end of June :(.

    Second, I checked out the code for 2.5 and couldn’t compile it (as with Itzik Kasovitch case). Could you please take a look into the problem he’s discovered?

    Third and most important! Thanks a lot for your excellent and extremely useful work on patterns in general (congrats on your MSDN article – pure pleasure to read) and StructureMap in particular.

  • Itzik Kasovitch

    I have checked out structuremap from sourceforge and tried to run the build script. Unfortunately, it failes. It seems that some files are missing. Should I make some settings to be able to run the build successfully. If so, where are the guidelines?

  • http://codebetter.com/blogs/jeremy.miller Jeremy D. Miller

    @Itzik,

    With 2.0, ObjectFactory.InjectStub(T object);

    With the 2.5 trunk, the above still works, but there are far more options.

    ObjectFactory.Inject(T object);

  • Itzik Kasovitch

    Is it possible to add components manually to structure map’s object factory? For example I want to create some object manually and the add it to structure map like it is done in WindsorContainer using AddComponent.

  • kasajian

    I got my hands dirty and learned DI/IoC by studying the crystalproject.org API. I found Simone Busoli’s introduction to it on dotnetslackers.com to be one of the best introductions on DI, if not one of the best articles written in general.

    So now understand it and am quite impressed with the cleanness of the crystal implementation. My plan was to study the other DI packages out there and then do a comparison, but frankly, when I start to go down the path of learning ObjectBuilder and even StructureMap, I quickly lose interest because the introductions start out more complex and convoluted than what crystal offers. I realize that I’m probably not being as fair to the other frameworks, but as many of us having relatively limited time, it seems as though there ought to be a better for people to decide between the different frameworks. There out to be a comparison article that does justice to the existing frameworks.

    Another thing that’s missing is that the DI introductions I’ve seen thus far focus on the programmatic use of the APIs, which some people prefer. But I strongly believe that the configuration based method has a lot more value. It would be good to have an introductory article to each of the DI frameworks for those shops that are planning on configuring the containers using external files and minimize the attributes and APIs in the code.

    Thank you for listening. :)

  • Suresh

    Hai Jeremy,

    I have a doubt in my application for using StructureMap.
    Can you tel me actually usage is like a Factory pattern.
    Is it right??

    In my application i got the instance of a Concrete class, it has more than 10 subclasses with the usage of n number of XmlSchema ( object). But the XmlSchema are use used in the different n number of Concrete classes..

    if i want to do any changes in one schema in one Concrete class that also depends on the n-1th concrete class ( Object dependency exists here.. ). can u tel me, can i use Structure map container, is it helpful for me…

    else can you tel me which pattern is optimal one..

    i need help

    my mail id is : vasuresh@jeevantechnologies.com

    Thanks

    Suresh

  • Yi

    Hello Jeremy,

    I just dropped an email to your yahoo mail. I encountered some issue when using StructureMap with Windows Service. The .NET runtime complains that “System.Runtime.Serialization.SerializationException: Unable to find assembly ‘StructureMap, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null’.” I double-checked that the structuremap.dll is in the working dir.

    I wonder if you used StructureMap with Windows Service. I hope you can shed me some light on this one.

    Thanks!!!

    Yi

  • Daniel Essin

    That would be great. Thanks.

  • jmiller

    Dan,

    The STAThread is a known issue, and if you’ll give me a little while I’ll get an example up showing how to use StructureMap sans config file to do exactly what you’re trying to do.

    Jeremy

  • Daniel Essin

    I’m very impressed with the work that you’ve done on StructureMap. I know that I need something like this that allows a degree of abstraction, but I’ve always been a bit challenged by higher math so I’m having a hard time absorbing all the fine points. I’ve got a couple of questions that you perhaps could help me with.

    First off, I want to mention that in order to run the StructureMap Explorer under .net 2.0 you need to as a [STAThread] attribute to the main or an exception is thrown when trying to create the browser component.

    I’m sure that you’re familiar with sharpDevelop. I am trying to do something like that – create a platform for my apps that will provide all of the basic services such as encryption, authentication, logging, etc. and into which all of the application-specific forms and functions will “plug in”

    I’ve studied the possibilty of simply using the sharpDevelop shell and replacing all of the content, using Spring.NET or using StructureMap. I’ve also looked as SAF (Simple application framework) by chen.

    I have stepped through the code in sharpDevelop dozens of times and I understand what it is doing pretty well but their external xl config files are so complex that every time I try to alter one the whole thing breaks. My opinion of that platform is that without a gui utility to examine your assemblies and write the .addin files, it will probably never work for me.
    I like the feature in Spring.NET of being able to embed the config for each assembly in a resurce and extract it during the load. This reduces the possibility that the config file will get lost, corrupted or damaged by a user trying to alter its behavior. For the same reason I like the idea of being able to accomplish the configuration of StructureMap by applying attributes to the classes.

    Am I correct in my understanding that what you have done in the StructureMap Explorer app is to have accomplished the entire configuation with attributes and that is why there is no .config file for the app?

    Becaus I am abstractionally challenged, I would appreciate it if you could give me some guidance about how to best have assemblies contribute items to the menubar,child forms that are invoked or affected by selecting different tree nodes (like in your explorer, and how I can osilate all of the commands that are executed in one place so the can be invoked form either a menu, form event or a use typing a command at a prompt?

    Thanks,
    Dan Essin (essin@ieee.org)

  • Yi

    Interesting. Can you give me an example about these “dynamic nodes and attributes”? Thank you in advance!

    Yi

  • jmiller

    Yi,

    I’ve never made one. Some of the nodes and attributes are dynamic, so it’s not really going to be possible anyway.

    Sorry,

    Jeremy

  • Yi

    Hello Jeremy,

    I wonder where I can find XSD file for the StructureMap.

    Thanks!

    Yi

  • Yi

    Thanks Jeremy! So by default, ObjectFactory creates new instance for each request. However, it reads config file and scans assemblies only once. I also find what you just said in the documentation:
    “New in version 1.0 is the ability to quickly define different creation modes. This functionality can be configured with the new optional “Scope” property on the [PluginFamily] attribute or the “Scope” attribute on the node.”

    I just put in an Authentication Plugin for my project. I was kind of curious if StructureMap will increase the memory usage. I barely notice the difference. Very nice work! :)

  • jmiller

    Yi,

    Not quite either. Unless you explicitly specify the Scope property ObjectFactory.GetInstance() will return a new instance per request.

    StructureMap largely caches the configuration. Scanning assemblies and parsing the StructureMap.config file only happens once on the first call to ObjectFactory (unless you force the issue with ObjectFactory.ResetDefaults()).

    Jeremy

  • Yi

    A quick question about ObjectFactory.GetInstance(typeof(IDatabase));.

    Does the OjbectFactory caches the instance or it reads the configuration file and search the assembly every time GetInstance is called?

  • Yi

    It’s really nice framework! I am going to use it in my project.