MVC3, Ninject, MvcSiteMapProvider - How to inject dependency to overridden method - asp.net-mvc

I have an MVC3 application that is using Ninject and MvcSiteMapProvider.
I have created this class which MvcSiteMapProvider uses to dynamically add nodes to my sitemap:
public class PageNodeProvider : DynamicNodeProviderBase
{
public override IEnumerable<DynamicNode> GetDynamicNodeCollection()
{
// need to get repository instance
var repository = // how do I get this???
foreach (var item in repository.GetItems())
{
yield return MakeDynamicNode(item);
}
}
}
The MvcSiteMapProvider instantiates this type itself, so I'm not sure how to inject my repository into it.
I thought about using service location by getting a handle on my kernel and calling Get<Repository>() in the method. But, I saw this property when looking at the definition of NinjectHttpApplication:
// Summary:
// Gets the kernel.
[Obsolete("Do not use Ninject as Service Locator")]
public IKernel Kernel { get; }
Do not use Ninject as Service Locator ?! How else am I supposed to do this?
I then found this question here on stackoverflow and all answers say don't use Service Location.
What am I supposed to do?

This seems to be another chapter from the book "Why providers are bad design?". You have the same problem as with any kind of ASP.NET providers. There are no really good and satisfying solutions for them. Just hacks.
I think the best option you have is to fork the project and change the DefaultSiteMapProvider to use DepencencyResolver instead of the Activator and provide the implementation back to the community. Then you can use constructor injection in your PageNodeProvider implementation. This will solve the problem once for all types and everyone.
Of course you could also use the DependencyResolver just in your implementation. But this is by far not the best solution because you should get the instances as close to the root as possible, it makes testing more complicated and it solves the problem just for you.

Even though I see that you've decided to ditch the provider altogether, I'd like to elaborate on using the DependencyResolver. Basically, you can manually get the correct repository instance via Ninject using
var repository = DependencyResolver.Current.GetService<IRepository>();
This is less robust, as you have to maintain this as well as the NinjectMVC3.cs class should the stuff change, and it is a bit more complicated to test.

Related

ASP.NET 5 / Core 1 Dependency Injection: Bad design or bad documentation?

I'm reading through the ASP.NET 5 docs and was choking on the chapter of dependency injection.
I am recommended to write my controllers like so:
public class MyController: Controller
{
private readonly MyService _myService;
public MyController(MyService myService)
{
_myService = myService;
}
public IActionResult Index()
{
// use _myService
}
}
The short and direct version is discouraged:
public class MyController : Controller
{
public IActionResult Index()
{
var myService = (MyService)HttpContext.RequestServices.GetService(typeof(MyService));
}
}
The given reason is because allegedly the recommended version...
[...] yields classes that are easier to test (see Testing) and are more loosely coupled.
The linked testing chapter doesn't shed any light on this weird statement.
I didn't look at the sources, but I assume whatever constructs the controller is using HttpContext.RequestServices.GetService itself to deliver the dependency? Clearly a test can setup a different implementation for testing, and clearly that is the whole point of a DI framework, right?
The colossus (MyService)HttpContext.RequestServices.GetService(typeof(MyService)) is bad enough, but a small helper could fix that (was a simple Get<MyService>() really so hard?).
But that this excessive clutter is recommended for basically every controller and more is disturbing.
It's all the more puzzling as there already is a Microsoft DI framework with a proper usage, MEF:
public class MyController : Controller
{
[Import]
private MyService _myService;
public IActionResult Index()
{
// use _myService
}
}
Why not at least just take that one? What's going on here?
This isn't a ASP.NET Core specific solution. This is how just about every DI framework works. The most common approach is to have all the dependencies of a controller as constructor parameters. This makes it clear what services the controller uses. There are multiple alternative solutions, but the basic idea stays the same and there are multiple pros and cons to them.
Clearly a test can setup a different implementation for testing, and clearly that is the whole point of a DI framework, right?
This line isn't clear to me. What do you think the 'whole point of a DI framework ' is? This line suggest you only use it so you can use a different implementation for testing.
But that this excessive clutter is recommended for basically every controller and more is disturbing.
Excessive clutter? What if I want to use MyService in two (or more) functions? Should I use this:
public class MyController : Controller
{
public IActionResult Index()
{
var myService = (MyService)HttpContext.RequestServices.GetService(typeof(MyService));
}
public IActionResult Index2()
{
var myService = (MyService)HttpContext.RequestServices.GetService(typeof(MyService));
}
}
Or should I opt for the solution where I set it up in the constructor? Seems like an obvious choice to me. In such a small example it may look like clutter, but add 10 lines of code to it and you'll barely notice a small constructor and some variable declarations.
You can use it while testing. It's a way to quickly grab something from the container when you need it, but it should certainly not be part of the actual code. You're simply hiding the dependency from sight.
At last you suggest property injection. This is a valid solution. But an often used argument against it is that it hides the dependency. If you define it as a parameter in the constructor you can't hide it. Besides, a lot of DI frameworks don't even have support for property or method injection because of this.
If you want to use MEF in your project you are free to do so. But it should, in my opinion, not be the default DI framework for ASP.NET. What's available right now is more than sufficient to do most tasks. If you need more functionality you can always use a different DI framework like StructureMap or AutoFac.
In the end it all comes down to what works for you. But stating this is either bad design or bad documentation is just wrong. You are of course free to prove me wrong on this. You could improve the ASP.NET documentation and/or would prove that the concept of inversion of control is wrong and suggest a better solution.

Using Ninject with Asp.NET Web API Beta ApiController

I'm stuck. I was using the method outlined here for wcf web api p6 Ninject working with WCF Web API Preview 5, however things are quite a bit different with the mvc implementation in the beta. There is a good article here http://www.asp.net/web-api/overview/extensibility/using-the-web-api-dependency-resolver that talks about building your own custom dependency resolver, however i would like to use the same implementation i'm using for my mvc view controllers...e.g. Ninject. I've tried a few things based on the IoC Unity example in the article too, but nothing has panned out yet. Any help pointing me in the right direction would be much appreciated. I'm going to keep digging on my own as well. Thanks in advance!
Here's where I'm at. I was using WebActivator to bootstrap the code but I've since dropped it to the Application_Start() just to take one more thing out of the equation.
protected void Application_Start()
{
var kernel = new StandardKernel(new MyNinjectModule());
GlobalConfiguration.Configuration.ServiceResolver.SetResolver(new NinjectDependencyResolver(kernel));
}
And am receiving the following error:
The type Ninject.Web.Mvc.NinjectDependencyResolver does not appear to implement Microsoft.Practices.ServiceLocation.IServiceLocator.Parameter name: commonServiceLocator
Found the solution
Perhaps there is/will be a more elegant way but this is now working for me. I'm also adding my custom message handler here as well.
[assembly: WebActivator.PreApplicationStartMethod(typeof(MyApp.AppStart.ApiBootstrapper), "Start")]
namespace MyApp.AppStart
{
public class ApiBootstrapper
{
public static void Start()
{
var kernel = new StandardKernel(new MyNinjectModule());
var resolver = new NinjectDependencyResolver(kernel);
GlobalConfiguration.Configuration.ServiceResolver.SetResolver(resolver.GetService, resolver.GetServices);
GlobalConfiguration.Configuration.MessageHandlers.Add(new ApiAuthHandler());
}
}
}
I never used the WebAPI but since the semantic of the IDependencyResolver is exactly the same as the one from MVC3 you should be able to use the same implementation: https://github.com/ninject/ninject.web.mvc/blob/master/mvc3/src/Ninject.Web.Mvc/NinjectDependencyResolver.cs
Update:
The Ninject.Web.WebAPi extension adds support for ApiControllers
I found the answer and updated my question above with the solution. The solution itself was more or less present in the Using the Web API Dependency Resolver article, i just had to keep tweaking for ninject. Both answers helped me quickly narrow this down so thanks to #Remo and #James.
May sound silly but have you made sure you have a reference to the CommonServiceLocator / CommonServiceLocator.NinjectAdapter nuget package or associated assemblies. Your NinjectDependencyResolver may not be able to resolve the reference to IServiceLocator.
The same code will work for both MVC and the WebApi, however because the WebApi was inspired by MVC and the MVC assemblies do not have to be referenced in order to use WebApi (or vise versa), there is a fair amount of duplication of code between the two frameworks. If you want to use MVC you're dependencies will come from System.Web.Mvc, if you want to use WebApi you'll use System.Web.Http. If you want to use both you'll have to differentiate in your code which to use when, using a more explicit namespace resolution.
In your case your problem is that MVC came first and the NinjectDependancyResolver class inherits from System.Web.Mvc.IDependencyResolver. You'll want to create an exact duplicate of the NinjectDependancyResolver class and instead inherit from System.Web.Http.IDependencyResolver instead. Use THIS class to setup your IoC and you'll be good to go.
I found a nice solution here.
It's pretty easy if you're already using the Ninject CommonServiceLocator / Bootstrapper:
private static IKernel CreateKernel() {
var kernel = new StandardKernel();
RegisterServices(kernel);
GlobalConfiguration.Configuration.ServiceResolver
.SetResolver(new NinjectServiceLocator(kernel));
return kernel;
}

The proper way to do Dependency Injection in a Windows Client (WPF) Application

I am used to IoC/DI in web applications - mainly Ninject with MVC3. My controller is created for me, filled in with all dependencies in place, subdependencies etc.
However, things are different in a thick client application. I have to create my own objects, or I have to revert to a service locator style approach where I ask the kernel (probably through some interface, to allow for testability) to give me an object complete with dependencies.
However, I have seen several places that Service Locator has been described as an anti-pattern.
So my question is - if I want to benefit from Ninject in my thick client app, is there a better/more proper way to get all this?
Testability
Proper DI / IoC
The least amount of coupling possible
Please note I am not just talking about MVVM here and getting view models into views. This is specifically triggered by a need to provide a repository type object from the kernel, and then have entities fetched from that repository injected with functionality (the data of course comes from the database, but they also need some objects as parameters depending on the state of the world, and Ninject knows how to provide that). Can I somehow do this without leaving both repositories and entities as untestable messes?
If anything is unclear, let me know. Thanks!
EDIT JULY 14th
I am sure that the two answers provided are probably correct. However, every fiber of my body is fighting this change; Some of it is probably caused by a lack of knowledge, but there is also one concrete reason why I have trouble seeing the elegance of this way of doing things;
I did not explain this well enough in the original question, but the thing is that I am writing a library that will be used by several (4-5 at first, maybe more later) WPF client applications. These applications all operate on the same domain model etc., so keeping it all in one library is the only way to stay DRY. However, there is also the chance that customers of this system will write their own clients - and I want them to have a simple, clean library to talk to. I don't want to force them to use DI in their Composition Root (using the term like Mark Seeman in his book) - because that HUGELY complicates things in comparison to them just newing up a MyCrazySystemAdapter() and using that.
Now, the MyCrazySystemAdapter (name chosen because I know people will disagree with me here) needs to be composed by subcomponents, and put together using DI. MyCrazySystemAdapter itself shouldn't need to be injected. It is the only interface the clients needs to use to talk to the system. So a client happily should get one of those, DI happens like magic behind the scenes, and the object is composed by many different objects using best practices and principles.
I do realize that this is going to be a controversial way of wanting to do things. However, I also know the people who are going to be clients of this API. If they see that they need to learn and wire up a DI system, and create their whole object structure ahead of time in their application entry point (Composition Root), instead of newing up a single object, they will give me the middle finger and go mess with the database directly and screw things up in ways you can hardly imagine.
TL;DR: Delivering a properly structured API is too much hassle for the client. My API needs to deliver a single object - constructed behind the scenes using DI and proper practices - that they can use. The real world some times trumps the desire to build everything backwards in order to stay true to patterns and practices.
I suggest to have a look at MVVM frameworks like Caliburn. They provide integration with IoC containers.
Basically, you should build up the complete application in your app.xaml. If some parts need to be created later because you do not yet know everything to create them at startup then inject a factory either as interface (see below) or Func (see Does Ninject support Func (auto generated factory)?) into the class that needs to create this instance. Both will be supported natively in the next Ninject release.
e.g.
public interface IFooFactory { IFoo CreateFoo(); }
public class FooFactory : IFooFactory
{
private IKernel kernel;
FooFactory(IKernel kernel)
{
this.kernel = kernel;
}
public IFoo CreateFoo()
{
this.kernel.Get<IFoo>();
}
}
Note that the factory implementation belongs logically to the container configuration and not to the implementation of your business classes.
I don't know anything about WPF or MVVM, but your question is basically about how to get stuff out of the container without using a Service Locator (or the container directly) all over the place, right?
If yes, I can show you an example.
The point is that you use a factory instead, which uses the container internally. This way, you are actually using the container in one place only.
Note: I will use an example with WinForms and not tied to a specific container (because, as I said, I don't know WPF...and I use Castle Windsor instead of NInject), but since your basic question is not specificaly tied to WPF/NInject, it should be easy for you to "port" my answer to WFP/NInject.
The factory looks like this:
public class Factory : IFactory
{
private readonly IContainer container;
public Factory(IContainer container)
{
this.container = container;
}
public T GetStuff<T>()
{
return (T)container.Resolve<T>();
}
}
The main form of your app gets this factory via constructor injection:
public partial class MainForm : Form
{
private readonly IFactory factory;
public MainForm(IFactory factory)
{
this.factory = factory;
InitializeComponent(); // or whatever needs to be done in a WPF form
}
}
The container is initialized when the app starts, and the main form is resolved (so it gets the factory via constructor injection).
static class Program
{
static void Main()
{
var container = new Container();
container.Register<MainForm>();
container.Register<IFactory, Factory>();
container.Register<IYourRepository, YourRepository>();
Application.Run(container.Resolve<MainForm>());
}
}
Now the main form can use the factory to get stuff like your repository out of the container:
var repo = this.factory.GetStuff<IYourRepository>();
repo.DoStuff();
If you have more forms and want to use the factory from there as well, you just need to inject the factory into these forms like into the main form, register the additional forms on startup as well and open them from the main form with the factory.
Is this what you wanted to know?
EDIT:
Ruben, of course you're right. My mistake.
The whole stuff in my answer was an old example that I had lying around somewhere, but I was in a hurry when I posted my answer and didn't read the context of my old example carefully enough.
My old example included having a main form, from which you can open any other form of the application. That's what the factory was for, so you don't have to inject every other form via constructor injection into the main form.
Instead, you can use the factory to open any new form:
var form = this.factory.GetStuff<IAnotherForm>();
form.Show();
Of course you don't need the factory just to get the repository from a form, as long as the repository is passed to the form via constructor injection.
If your app consists of only a few forms, you don't need the factory at all, you can just pass the forms via constructor injection as well:
public partial class MainForm : Form
{
private readonly IAnotherForm form;
// pass AnotherForm via constructor injection
public MainForm(IAnotherForm form)
{
this.form = form;
InitializeComponent(); // or whatever needs to be done in a WPF form
}
// open AnotherForm
private void Button1_Click(object sender, EventArgs e)
{
this.form.Show();
}
}
public partial class AnotherForm : Form
{
private readonly IRepository repo;
// pass the repository via constructor injection
public AnotherForm(IRepository repo)
{
this.repo= repo;
InitializeComponent(); // or whatever needs to be done in a WPF form
// use the repository
this.repo.DoStuff();
}
}

DDD and constructor explosion

I'm practicing DDD with ASP.NET MVC and come to a situation where my controllers have many dependencies on different services and repositories, and testing becomes very tedious.
In general, I have a service or repository for each aggregate root. Consider a page which will list a customer, along with it's orders and a dropdown of different packages and sellers. All of those types are aggregate roots. For this to work, I need a CustomerService, OrderService, PackageRepository and a UserRepository. Like this:
public class OrderController {
public OrderController(Customerservice customerService,
OrderService orderService, Repository<Package> packageRepository,
Repository<User> userRepository)
{
_customerService = customerService
..
}
}
Imagine the number of dependencies and constructor parameters required to render a more complex view.
Maybe I'm approaching my service layer wrong; I could have a CustomerService which takes care of all this, but my service constructor will then explode. I think I'm violating SRP too much.
I think I'm violating SRP too much.
Bingo.
I find that using a command processing layer makes my applications architecture cleaner and more consistent.
Basically, each service method becomes a command handler class (and the method parameters become a command class), and every query is also its own class.
This won't actually reduce your dependencies - your query will likely still require those same couple of services and repositories to provide the correct data; however, when using an IoC framework like Ninject or Spring it won't matter because they will inject what is needed up the whole chain - and testing should be much easier as a dependency on a specific query is easier to fill and test than a dependency on a service class with many marginally related methods.
Also, now the relationship between the Controller and its dependencies is clear, logic has been removed from the Controller, and the query and command classes are more focused on their individual responsibilities.
Yes, this does cause a bit of an explosion of classes and files. Employing proper Object Oriented Programming will tend to do that. But, frankly, what's easier to find/organize/manage - a function in a file of dozens of other semi-related functions or a single file in a directory of dozens of semi-related files. I think that latter hands down.
Code Better had a blog post recently that nearly matches my preferred way of organizing controllers and commands in an MVC app.
Well you can solve this issue easily by using the RenderAction. Just create separate controllers or introduce child actions in those controllers. Now in the main view call render actions with the required parameters. This will give you a nice composite view.
Why not have a service for this scenario to return a view model for you? That way you only have one dependency in the controller although your service may have the separate dependencies
the book dependency injection in .net suggests introducing "facade services" where you'd group related services together then inject the facade instead if you feel like you have too many constructor parameters.
Update: I finally had some available time, so I ended up finally creating an implementation for what I was talking about in my post below. My implementation is:
public class WindsorServiceFactory : IServiceFactory
{
protected IWindsorContainer _container;
public WindsorServiceFactory(IWindsorContainer windsorContainer)
{
_container = windsorContainer;
}
public ServiceType GetService<ServiceType>() where ServiceType : class
{
// Use windsor to resolve the service class. If the dependency can't be resolved throw an exception
try { return _container.Resolve<ServiceType>(); }
catch (ComponentNotFoundException) { throw new ServiceNotFoundException(typeof(ServiceType)); }
}
}
All that is needed now is to pass my IServiceFactory into my controller constructors, and I am now able to keep my constructors clean while still allowing easy (and flexible) unit tests. More details can be found at my blog blog if you are interested.
I have noticed the same issue creeping up in my MVC app, and your question got me thinking of how I want to handle this. As I'm using a command and query approach (where each action or query is a separate service class) my controllers are already getting out of hand, and will probably be even worse later on.
After thinking about this I think the route I am going to look at going is to create a SerivceFactory class, which would look like:
public class ServiceFactory
{
public ServiceFactory( UserService userService, CustomerService customerService, etc...)
{
// Code to set private service references here
}
public T GetService<T>(Type serviceType) where T : IService
{
// Determine if serviceType is a valid service type,
// and return the instantiated version of that service class
// otherwise throw error
}
}
Note that I wrote this up in Notepad++ off hand so I am pretty sure I got the generics part of the GetService method syntactically wrong , but that's the general idea. So then your controller will end up looking like this:
public class OrderController {
public OrderController(ServiceFactory factory) {
_factory = factory;
}
}
You would then have IoC instantiate your ServiceFactory instance, and everything should work as expected.
The good part about this is that if you realize that you have to use the ProductService class in your controller, you don't have to mess with controller's constructor at all, you only have to just call _factory.GetService() for your intended service in the action method.
Finally, this approach allows you to still mock services out (one of the big reasons for using IoC and passing them straight into the controller's constructor) by just creating a new ServiceFactory in your test code with the mocked services passed in (the rest left as null).
I think this will keep a good balance out the best world of flexibility and testability, and keeps service instantiation in one spot.
After typing this all out I'm actually excited to go home and implement this in my app :)

Share Object to all Users of mvc Webapp

My web App prepares out of a db for one or two minutes a specific and read-only object list, once only when IIS starts. This does not change any more unless the admin triggers recreation by a specific URL.
The Interface of the objects looks like this:
public interface IProductsRepository {
IQueryable<Row1> ProductItmes { get; }
IQueryable<Row2> ProductLegItems { get; }
}
I am now not really sure where i put the object so it is accessible from any controller.
Should i put the load method to protected void Application_Start() as a static object? What is the best approach?
you need to use a dependency injection framework here so you can instantiate this one and pass it into all of your controllers. This doesn't come out of the box with asp.net-mvc but you can find a number of options that will do the trick like castle windsor or autofac
This may or may not meet your needs but Castle Windsor allows you to specify how many instances a component (like a data repository) will have. I personally had a typo when working with this (lifesyle instead of lifestyle) that resulted in the data repository persisting after a post without my initializing it.
http://www.castleproject.org/container/documentation/trunk/usersguide/lifestyles.html
A good place would be the the Cache. You can load the Cache on Application_Start()
You can store it in Application object, but you should inject it into Controller. You shouldn't reference directly Application object, because this will make your application less testable. I use Ninject (http://ninject.org/) for this purpose.

Resources