Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Dependency Injection and project structure for Console applications

I have 4 projects:

Core (IServer):

  • System
  • System.Core

DependencyResolver:

  • Core
  • StructureMap

Infrastructure (Service):

  • Core
  • External dependency

Console:

  • Core
  • DependencyResolver

Requierements:

I am trying to use StructureMap only in the DependencyResolver. Furthermore the Console application should not know anything about Infrastucture.

When I do not want to reference StructureMap on my Console Application I have to build a ServiceLocator.

In the DependencyResolver I have a Bootstrapper that is responsible for calling StructureMap registry stuff (Register)

In my Console application I want to get an instance. For this I need to reference StructureMap. Another way would be to write a little wrapper around StructureMaps resolving methods.

Is there any other better way of decoupling the console from StructureMap?

like image 223
Rookian Avatar asked Mar 21 '12 14:03

Rookian


1 Answers

While I see a reason for separating IoC register,resolve,release from the implementation of the application, I don't see any reason why the IoC container shouldn't be in the console application (the composition root) and the application implemention in another assembly instead.

That way the console application is very easy:

  1. Create the container
  2. Load the container configuration
  3. Resolve the Application
  4. Call run on the application and pass the console arguments along
  5. dispose the container when the application exits the run method

With SM it look about like this:

public void Main(params string[] args)
{
    using (var container = new Container())
    {
        container.LoadAllConfigurationModules();
        container.AddRegistry<SomeRegistry>();
        container.GetInstance<Application>().Run(args);
    }
}

For things you can't create at startup you create a factory interface in your application assembly:

interface ISomeFactory { ISomeDependency CreateSomeDependency() }

and implement this interface in the console application by injecting the container and use it to resolve the instance. I guess the SM implementation looks like this:

public class SomeFactory : ISomeFactory
{
    public SomeFactory(IContainer sontainer) { this.container = container; }
    ISomeDependency CreateSomeDependency() { this.container.GetInstance<ISomeDependency>(); }
}

Other IoC container even have the functionallity to implement these interface factories automatically.

like image 106
Remo Gloor Avatar answered Oct 21 '22 09:10

Remo Gloor