Registering the Repository in the DI Container

Right, the magic of Dependency Injection containers. Let’s start small by registering our MockRepository against the IRepository<ToDoItem> interface, and using the DI container to retrieve it in our View.

I’m going to register the interface inside the App’s constructor. This is cross-platform, so it’s the constructor inside the .NET Standard library, not the platform-specific projects.

This tells my DI container to give me an instance of my MockRepository class every time I ask for an IRepository<ToDoItem>. Since that’s exactly what I need for my View, I can change that to:

as a First step. Go and set a breakpoint where you retrieve the repo from the DI container, and you’ll see that you get an instance of a MockRepository when you ask for an IRepository<ToDoItem>.

The most important thing here is that the View is now decoupled from the MockRepository, i.e. it doesn’t decide which concrete class should be used as a repository. That means that when, later on, we want to use a real repository instead of our mockup, we only have to change the registration in our App’s constructor, rather than having to hunt down every line where we’re creating a new instance of a class that takes an IRepository as a constructor argument.

That said, this can still be improved upon – more on that in the next post.

Handling Dependency Injection in the View

OK, after all that testing, let’s head back to the app itself, where we have introduced a bit of a problem when we changed the View Model to use Dependency Injection via the constructor.

Just to recap: Here is the current constructor for our ViewModel, where we’re injecting our repository (just the relevant bits):

… and here is our current View:

As it stands, the ViewModel is going to throw an ArgumentNullException, so we need to do something about that.

Now, the quick and dirty way to handle this would be to create the repository in the constructor for our View and inject it right there, but that violates the principles of MVVM big time. The View should have no knowledge of, well, pretty much anything except for the ViewModel (ideally).

Furthermore, creating an instance of the ViewModel creates tight coupling. In my opinion, since it’s between two classes that are very closely related, that might be acceptable. Still, loose coupling would be preferable.

A popular solution to this problem is to use a Dependency Injection Container, and, as luck would have it, there’s a very simple one, called SimpleIoc, baked into the MVVMLight package.

Again, there’s tons to read about DI containers, and I’d encourage you to do so. For now, let’s stick to the very basics: a DI container allows you to register a class for retrieval later, BUT it also does allow you to register a class against an interface and, by magic, will substitute those interfaces for the registered classes when found in a constructor.

Yes, that sounds complicated, but in practice it really isn’t. Over the next few posts I’m going to walk you through the process, step-by-step.