1

Is it possible to use StructureMap to scan assemblies to be aware of concrete classes that do not implement interfaces? I am fairly new to StructureMap so not sure if this should be an obvious thing.

For context, below are the highlights of the classes I am working with. UserController depends on an instance of UserManager which depends on an instance of IUserRepository.

public interface IUserRepository { }

public class UserRepository { }

public class UserManager
{
    public UserManager(IUserRepository repository) { }
}

public class UserController
{
    public UserController(UserManager manager) { }
}

This is the code I have in my Startup.ConfigureServices method to do the scanning for DI:

// Setup dependencies using StructureMap
var container = new Container(x =>
{
    x.Scan(s =>
    {
        s.AssemblyContainingType<UserRepository>();
        s.WithDefaultConventions();
    });
});

container.Populate(services);

The problem is I get the following error:

Unable to resolve service for type 'UserManager' while attempting to activate 'UserController'.

If I add the following line to Startup.ConfigureServices then it works, but I am looking for a solution that doesn't require me to have a line for every manager. I have been thinking StructureMap assembly scanning could solve this but I am open to other solutions as well.

services.AddTransient<UserManager>();
Bernd
  • 330
  • 1
  • 2
  • 7
  • 1
    I would reconsider your architecture. You could use StructureMap as your DI container, but if you do so, it should handle all your dependencies and you can eliminate the reliance on the built in container. As far as scanning for dependencies, if you're only going to have one concrete object that doesn't implement an interface or abstract class then you might as well just hard code the object reference anyway as there is no opportunity for substitution when your container already references the concrete class. Scanning assemblies would be akin to a service locator pattern which is frowned upon. – cygnim Mar 09 '16 at 17:28
  • @Phasiq your comment made me step back and think. Since I always know what concrete class to use for the UserManager within the UserController I do not need to use DI to create that dependency and can instead create it within the controller as needed, is this what you were suggesting? – Bernd Mar 09 '16 at 18:07
  • Well, sort of. If you have a hard dependency on a concrete class, then having it instantiated with a DI container really isn't necessary and provides little benefit. But, I would really think about future flexibility and testing. Having your class implement an interface/abstract class will definitely help guard against future changes blowing up your existing architecture. There is a time and place for strict dependence, but I've found it to be rare in controller classes. If you're writing unit tests, I'd definitely implement an interface or abstract class. – cygnim Mar 09 '16 at 19:03
  • @Phasiq Got it, if I construct the concrete dependencies in the UserManager class then I for sure end up with a service locator pattern because I have to pass the Container to the controller to do the resolution of the other dependencies. I'm not interested in testing my controllers though, they will just call the Managers and shouldn't have any logic needing testing within them. This leaves me with libraries that I can use in other projects with minimal code duplicated. – Bernd Mar 10 '16 at 02:13
  • Have I ended up with an onion architecture that is discouraged here: http://structuremap.github.io/best-practices/? – Bernd Mar 10 '16 at 03:39
  • Same situation. Are you able to solve this? – Ajmal VH Aug 24 '16 at 06:42
  • @AjmalVH I ended up using Interfaces so I could use StructureMap's scan. – Bernd Aug 25 '16 at 11:56

1 Answers1

1

Add .AddControllersAsServices() extention method to your services.AddMvc() call.

Result:

services.AddMvc().AddControllersAsServices();
xeeqqw
  • 49
  • 1
  • 5