Using MEF, let's imagine there is a class called FooType and I apply the [Export] attribute on it. Now, I want to import this FooType somewhere else in my code to use it.
I have tried these two solutions :
[Import]
public FooType Foo { get; set; }
private void MyMethod()
{
Foo.DoSomething();
}
and
private void MyMethod()
{
// _container is of type CompositionContainer and comes from the [ImportingConstructor]
_container.GetExportedValue<FooType>().DoSomething();
}
Both of these worked, the DoSomething() method of FooType is correctly called. So it makes me wonder:
Are these two way of resolving an export really similar ? Or is there any difference ?
Is there recommanded solution between the two ?
An [Import] basically causes MEF to call GetExportedValue and assign it to the property or field. That said, most of the time you don't want your objects to have access to your container. In your second example you said you imported the container itself via ImportingConstructor. I would usually only import FooType via the constructor. I also always prefer constructor injection rather then property injection. It makes the pre-requisites of the object totally clear and your imports can be stored in readonly properties.
Related
I've been gifted having had to work with an already set up Ninject DI based application which I have grown and added to considerably over the development of an application I'm working on.
I now find a problem that I would like to correct. I've managed to work around it using inheritance but would like a more cleaner solution.
I have two connections required to be injected into different services and repositories. I then need the repositories to also be correctly linked to the correct service having the same UnitOfWork.
I think I might be asking something that is not possible without inheritance and specialisation but that is why I am asking.
I managed to resolve this by creating a sub class of the main Repository and UnitOfWork classes but does nothing apart from implementing the base class.
I just don't like the idea of a sub class that is fully dependant on the super class functionality with basically empty braces apart from constructor, to me this doesn't seem true OOP just to resolve this problem. So I sought for a better solution utilising a one class solution if possible in DI.
So if you can ignore the solution I have spoken about because I completely reverted the change this is what I am left with:
Looking at the code below you can see what is the objective.
...
public class UnitOfWork : IUnitOfWork
{
private static readonly log4net.ILog log = log4net.LogManager.GetLogger("UnitOfWork");
public DbContext DataContext { get; set; }
public UnitOfWork(string connectionString)
{
DataContext = new DbContext(connectionString);
}
public void Commit()
{
...
}
}
...
public class Repository<T> : IRepository<T> where T : class
{
public IUnitOfWork unitOfWork { get; set; }
private readonly IDbSet<T> dbSet;
//private static readonly log4net.ILog log = log4net.LogManager.GetLogger("Repository");
public Repository(IUnitOfWork unitOfWork)
{
this.unitOfWork = unitOfWork;
dbSet = this.unitOfWork.DataContext.Set<T>();
}
...
}
...
public class IPOPDataModules : NinjectModule
{
public override void Load()
{
Bind<IUnitOfWork>().To<UnitOfWork>().InRequestScope().WithConstructorArgument("connectionString", ConfigurationManager.ConnectionStrings["IPOP_BE_TESTEntities"].ConnectionString);
Bind<IRepository<tOrder>>().To<Repository<tOrder>>().InRequestScope();
}
}
...
public class DataModules : NinjectModule
{
public override void Load()
{
Bind<IUnitOfWork>().To<UnitOfWork>().InRequestScope().WithConstructorArgument("connectionString", ConfigurationManager.ConnectionStrings["IPOP_BAPSEntities"].ConnectionString);
Bind<IRepository<Data.Quote>>().To<Repository<Data.Quote>>().InRequestScope();
}
}
...
public class QuoteService : IQuoteService
{
private IUnitOfWork unitOfWork;
private IRepository<Data.Quote> quoteRepository;
public QuoteService(IUnitOfWork unitOfWork, IRepository<Data.Quote> quoteRepository)
{
...
}
}
...
public class IPOPService : IIPOPService
{
private IUnitOfWork unitOfWork;
private IRepository<Data.tOrder> tOrderRepository;
public IPOPService(IUnitOfWork unitOfWork, IRepository<Data.tOrder>)
{
...
}
}
What I want to know is, is it possible to share the same UnitOfWork and Repository objects by two different connections and have them injected as different instances to the respective services (IPOPService for IPOP_BE_TEST connection, QuoteService for IPOP_BAP connection)
Again the code above doesn't achieve want I want but this is the sort of architecture I would like to play around to get this to work.
What you're looking for are Ninject binding scopes. Whenever you declare a binding Ninject will provide a delegate to that binding that the activation process uses to determine if it should create a new instance of that service, or if it should return a previously constructed instance.
So, if you want to implement a singleton in Ninject, you simply declare a binding that looks like this:
Bind<IRepository<Data.Quote>>().To<Repository<Data.Quote>>().InSingletonScope();
InSingletonScope() and InRequestScope() are simply sugar (or in the case of InRequestScope an extension method) on IBindingInSyntax<T> for the InScope(Func<Ninject.Activation.IContext, object> scope) method though. Any time you want to ensure that Ninject returns the same instance of a service in a given situation, all you need to do is implement a custom scope.
If I understand your question correctly, you want to ensure that when a request hits your application the same instances of Repository<T> and IUnitOfWork will be injected into all the services in your application. In this case you would simply have to write bindings like this:
Bind<IUnitOfWork>().To<UnitOfWork>().InRequestScope().WithConstructorArgument("connectionString", ConfigurationManager.ConnectionStrings["IPOP_BE_TESTEntities"].ConnectionString);
Bind<IRepository<tOrder>>().To<Repository<tOrder>>().InRequestScope();
However, your problem appears to be that you have two separate modules, with two separate bindings. I would suggest that you need to use a single module with contextual binding to determine which connection string should be provided to which part of the system. So your one module might look like this:
Bind<IUnitOfWork>()
.To<UnitOfWork>()
.WhenInjectedInto<IIPOPService>()
.InRequestScope()
.WithConstructorArgument("connectionString", ConfigurationManager.ConnectionStrings["IPOP_BE_TESTEntities"].ConnectionString);
Bind<IUnitOfWork>()
.To<UnitOfWork>()
.WhenInjectedInto<IQuoteService>()
.InRequestScope()
.WithConstructorArgument("connectionString", ConfigurationManager.ConnectionStrings["IPOP_BAPSEntities"].ConnectionString);
Bind<IRepository<tOrder>>().To<Repository<tOrder>>().InRequestScope();
This way you can be sure that when Ninject is resolving IIPOPService it will create an instance of UnitOfWork initialized with the "IPOP_BE_TESTEntities" connection string, and when resolving IQuoteService, it will use the "IPOP_BAPSEntities" connection string, but otherwise, across that request scope, only a single instance will be constructed by Ninject.
Hope this helps.
Your question is not completely clear for me. But check the documentation for the following two scopes, which might be interesting for your scenario.
InCallScope will result that only one instance will be created per resolution tree. I usually use this scope on desktop applications for a unit of work. See the documentation here. You'll need the Ninject.Extensions.NamedScope extension for this.
InRequestScope will result that in a web application, only one instance will be created per HTTP request. I usually use this scope for a unit of work. See the documentation here. You'll need the Ninject.Web.Common package for this.
I find myself adding dependencies a lot to constructors like so:
public class SomeClass() {
private ISomeService _service;
private IAnotherService _anotherService;
public SomeClass(ISomeService service, IAnotherService anotherService) {
_service = service;
_anotherService = anotherService;
}
}
They're quite tedious to write, I've been looking for code snippets in visual studio to automatically add one to the constructor but haven't found one.
What I want is:
When adding a dependency to a constructor some snippet automatically creates a local variable and assigns to it.
OR
Add a private variable and then some snippet automatically adds it to the constructor and assigns it to the local variable.
If you have R# you can enter the field declarations and then highlight them and hit Alt-Enter which will give you the option to generate the constructor and field assignments.
If you don't have Resharper, you can add the parameter on the constructor, write the assignament to an unexisting property and hit CTRL+. . This will prompt you with the options to automatically create a property or field for you.
For example, you have this class:
public class MyClass
{
public MyClass()
{
}
}
You then add the parameter to the constructor, and the assignament:
public class MyClass
{
public MyClass(IDependency myDependency)
{
this.myDependency = myDependency;
}
}
And hit CTRL+. while on the asignament line, and select create field, and you'll get this:
public class MyClass
{
IDependency myDependency;
public MyClass(IDependency myDependency)
{
this.myDependency = myDependency;
}
}
I don't know about previous versions, but in vanilla Visual Studio 2017, you can actually add a constructor parameter
public SomeClass(ISomeService service)
{
}
Then put your cursor on service and from "Quick actions" you can chose Introduce and initialize field _someService which will do what you want :
private readonly ISomeService _someService;
public SomeClass(ISomeService service)
{
_someService = service;
}
You can easily add code snippets as you like, defining it in XAML and adding it the editior, you can use place holders like "class name" to use it as a constructor for example, and then place your variables in it as static text
I don't want to write the code because it's duplicated
you can check out how to do it here:
https://msdn.microsoft.com/en-us/library/ms242312.aspx?f=255&MSPPError=-2147217396
you can also see this question:
How can I automatically generate a constructor that receives and stores services for free?
what you are trying to do with the ISomeService and IAnotherService is to do dependency inversion.
I would strongly recommend you combine this with a dependency injection framework. There are many available but one i would recommend is MEF. MEF is build into the .net framework. For example your code would look like this with MEF
[Export(typeof(ISomeService))]
public class SomeService : ISomeService {
}
public class SomeClass {
[Import]
public ISomeService SomeService {get; set;}
[Import]
public IAnotherService AnotherService {get; set;}
}
Now MEF will actually ensure your SomeService and AnotherService Properties are filled when your class is created. It will construct (if needed) a instance of SomeService, fill all it's dependencies and put it in the right property. You can even control if you want your services instantiated as singletons or as a new service instance each time you need one.
for more details on MEF you can look here https://msdn.microsoft.com/en-us/library/ee155691(v=vs.110).aspx
This should avoid writing the many constructors that do nothing other than initializing services.
Telerik's JustCode can do exactly what you need.
if you have an unused argument in the constructor you can create a field and initialise it.
http://www.telerik.com/products/justcode/quick-fixes.aspx
I was looking for exactly this when I found this library of snippets. Depending on how many parameters you need, you can use ctor1p, ctor2p.. so on. It creates the constructor with number of params specified and also generates a private field corresponding to each of the injected param.
It works just fine when you're writing the constructor for the first time.
If you have an existing constructor with/without parameters and you'd like to inject a new parameter using these snippets, you will have to rewrite your constructor which will be difficult than just injecting the parameter manually and using ctrl + ..
I have a service class in a module in Orchard CMS that it is dependent on some dependency such as IContentManager and it implemented IDependency interface.
in my controllers i used it by injecting and it works pretty good.
my service:
public class AddressService : IAddressService
{
private readonly IContentManager _contentManager;
private readonly IOrchardServices _orchardService;
private readonly IRepository<StatePartRecord> _stateRepository;
private readonly IContentDefinitionManager _contentDefinitionManager;
public AddressService(IContentManager contentManager, IOrchardServices orchardService, IRepository<StatePartRecord> stateRepository, IContentDefinitionManager contentDefinitionManager)
{
_contentManager = contentManager;
_orchardService = orchardService;
_stateRepository = stateRepository;
_contentDefinitionManager = contentDefinitionManager;
}
...
}
public interface IAddressService : IDependency { ... }
my question is that, in my custom class that is just a simple class how do i resolve and create an object instance of my service class in it?
my simple class:
public class MyClass
{
public SomeMethod()
{
var addressService = // a method to resolve 'AddressService' class from IOC container
// Do somthing with 'addressService' ...
}
}
Edit I already knew that we can use AddressService by injecting way, but i can't use injection in some cases such as static classes or extension method... ,Because of that i need to resolve dynamically AddressService and create instance by some method (that i guess it would be found in Orchard Framework) where i had to use it.
In fact I need a method that takes a Type as argument and create instance of the passed Type and return the created object.
You don't. Your class itself will have to be instantiated by something. It should be instantiated when injected into something else. This question should be modified to present a real example rather than a "hello world what if" scenario.
Why not register your other class into the Autofac container also? Then you could let your container take care of wiring up your class. Its not good idea to have reference to service which is managed by Autofac injected into class that is not. Services should be injected into controllers that are managed. If you need to combine service functionality just make another service where you can do that....
Otherwise, you need a reference to Autofac Container and then call the Resolve method. So, how you get that? You can look at how that is done in DefaultContentManager where componets are resolvet through IComponentContext, but of course DefaultContentManager is managed by Autofac and there is no static method that I could find in Orchard that will let you get the reference to the Autofac container (if there were it would be a static getter in OrchardStarter).
Pass an argument (the service) into the constructor which implements the interface. Then you should be able to access the service (IOC Sorts out instantiation etc):
public class MyClass
{
private IAddressService addressService;
public MyClass(IAddressService service)
{
addressService = service;
}
public SomeMethod()
{
// Do something with 'addressService' ...
}
}
Or is your question not as obvious as what I have understood it to be??
On fifth reading of your question, I think you may be asking how to register your interface so that it uses your implementation?
Not sure how Ioc is done in Orchard but in Windsor (which I use at work) we register dependencies similar to this:
public class MyClass
{
public SomeMethod(IWindsorContainer container)
{
container.Register( Component.For<IAddressService>().ImplementedBy<AddressService>());
}
}
EDIT: Made mistake in code so added constructor, instead of passing the value to the method.
I resolved using IWorkContexAccessor.
You can see code here.
I am really interested in some architectural methods. I like DI and IOC, but I don't understand costructor injection; why is it so complicated. I've written the code below which uses constructor injection:
namespace DependencyInjection
{
class Program
{
static void Main(string[] args)
{
ConstructorInjectionClass myCtx = new ConstructorInjectionClass(new PdfFormat());
myCtx.Print();
Console.Read();
}
}
public interface IFormat
{
void Print();
}
public class PdfFormat : IFormat
{
public void Print()
{
Console.WriteLine("Pdf Format Print is completed...");
}
}
// Constructor Injection
public class ConstructorInjectionClass
{
private IFormat _format;
public ConstructorInjectionClass(IFormat format)
{
_format = format;
}
public void Print()
{
_format.Print();
}
}
I've written some code below. I think it's simple.
public interface IFormat
{
void Print();
}
public class PdfFormat : IFormat
{
public void Print()
{
Console.WriteLine("Pdf Format Print is completed...");
}
}
public interface ISave
{
void Add();
}
public class Sql: ISave
{
public void Add()
{
Console.WriteLine("Adding to SQL is completed...");
}
}
// Constructor Injection
public class ConstructorInjectionClass
{
public ConstructorInjectionClass(IFormat format)
{
format.Print();
}
public ConstructorInjectionClass(ISave saver)
{
saver.Add();
}
Why should I use constructor injection? Advantages or disadvantages of these two methods?
The first example is constructor injection. You are injecting the class with the responsibility for printing into the class.
In the second example you are creating a new class with one of 2 arguments and using the argument in the constructor. This is bad for several reasons:
Your constructor should not really do significant work, this is either saving or printing in the constructor
Your different constructors are doing different this. The constructor should only create a new instance of your class.
It is not clear that the different constructors will actually do something when they are given different objects.
If you pass the objects to the constructor and then it just calls them, why would you not just have the code that is constructing this class call the methods on ISave and IPrint implementations. After all it must have them to be able to pass them to the method. If your object holds these internally then they could have been provided when your object was constructed (like in your composition root) and the client code that calls Print on your object would not need to know anything about the fact that the ISave and IPrint implementations exist,
Constructor injection is about you class asking for the dependencies it has in it's constructor, so it is clear what the dependencies are. By requiring the dependencies rather than creating them it becomes simpler to test the class as you can inject mock dependencies for testing purposes.
The first option is good, and if you want to add saving then you should add an extra argument to the constructor to take a ISave interface as well as the IPrint interface and have a method Save which will delegate to the ISave implmentation.
By having the dependencies injected and by programming to an interface it makes it easier to change the functionality later on. You could, for example, make it pring to a file easily (by changing the IPrint interface you pass in or change it to save to an xml file or a webservice by changing the ISave implementation you pass it. This make you class loosely coupled to the save and print implemenations
I would read this excellent answer for more guidance on DI/IOC
Well, as with any pattern, constructor injection should be used when and only when it's a good idea to use it. Your example code is kind of strange...
Your first example is spot on. Your class has a method called Print which has a dependency on another class to do the printing. Rather than instantiate this dependency, it requires that the dependency be supplied in its constructor. This is a classic example of the Dependency Inversion Principle. Basically: "Require, don't instantiate."
Your second example isn't quite clear, though. What is your class really doing? What's it for? It has two constructors which perform an action on their dependencies, but why? Nowhere else in the class is there a dependency on instances of these types. So why have the wrapper class in the first place? It seems more... contrived... than your first example. It's unclear what the architecture of the code is trying to accomplish, and therefore as it stands not a good use of constructor injection.
Lets say that you want to inject dependencies... you could do this via constructor injection or via property setters. I think one of the advantages to constructor injection is that IOC's use this strategy. So if you aren't sure you want to go IOC but you want to do DI then should probably use constructor injection to make the transition to IOC latter... easier... if you should change your mind...
Consider the following code.
public interface IFoo { }
public class Bar
{
public Bar(IFoo[] foos) { }
}
public class MyModule : NinjectModule
{
public override void Load()
{
Bind<IFoo[]>().ToConstant(new IFoo[0]);
// ToConstant() is just an example
}
}
public class Program
{
private static void Main(string[] args)
{
var kernel = new StandardKernel(new MyModule());
var bar = kernel.Get<Bar>();
}
}
When I try to run the program I get the following exception.
Error activating IFoo
No matching bindings are available, and the type is not self-bindable.
Activation path:
2) Injection of dependency IFoo into parameter foos of constructor of type Bar
1) Request for Bar
How can I inject / bind to an array in Ninject?
Thanks for your time.
Edit:
My application imports data which is created by a third party component.
The import process applies different kind of filters (e.g. implementations of different filter interfaces). The rules for filtering change quite often but are too complex to be done with pure configuration (and a master filter).
I want to make adding/editing filters as easy as possible. What I have is an assembly where all the filter implementations are located in. I tried to bind every filter interface to the following method (which provides an instance of every implementation of that filter type). Basically I want to avoid the need to change my Ninject module when I add/remove filter classes.
private IEnumerable<TInterface> GetInterfaceImplementations<TInterface>(IContext context)
{
return GetType().Assembly.GetTypes()
.Where(t => typeof (TInterface).IsAssignableFrom(t) && IsConcreteClass(t))
.Select(t => Kernel.Get(t)).Cast<TInterface>();
}
I am feeling a bit guilty in terms of bypassing the containers DI mechanism. Is this a bad practice? Is there a common practice to do such things?
Resolution:
I use a wrapper class as bsnote suggested.
Ninject supports multi injection which would resolve your issue. https://github.com/ninject/ninject/wiki/Multi-injection
public interface IFoo { }
public class FooA : IFoo {}
public class FooB : IFoo {}
public class Bar
{
//array injected will contain [ FooA, FooB ]
public Bar(IFoo[] foos) { }
}
public class MyModule : NinjectModule
{
public override void Load()
{
Bind<IFoo>().To<FooA>();
Bind<IFoo>().To<FooB>();
//etc..
}
}
This is largely a restatement of #bsnote's answer (which I've +1d) which may help in understanding why it works in this manner.
Ninject (and other DI / addin frameworks) have two distinct facilities:
the notion of either binding to a single unambiguous implementation of a service (Get)
A facility that allows one to get a set of services [that one then programmatically picks one of or aggregates across in some way] (GetAll / ResolveAll in Ninject)
Your example code happens to use syntax that's associated with 2. above. (e.g., in MEF, one typically use [ImportMany] annotations to make this clear)
I'd need to look in the samples (look at the source - its really short, clean and easy to follow) to find a workaround for this.
However, as #bsnote says, one way of refactoring your requirement is to wrap the array either in a container, or to have an object that you ask for it (i.e., a factory method or repository type construct)
It may also be useful for you to explain what your real case is - why is there a naked array ? Surely there is a collection of items construct begging to be encapsulated underlying all this - this question certainly doesnt come up much?
EDIT: There are a set of scanning examples in the extensions that I imagine would attack a lot of the stuff you're trying to do (In things like StructureMap, this sort of stuff is more integrated, which obviously has pros and cons).
Depending on whether you're trying to achieve convention over configuration or not, you might want to consider sticking a marker interface on each type of plugin. Then you can explicitly Bind each one. Alternately, for CoC, you can make the Module's Load() routine loop over the set of implementations you generate (i.e., lots of individual Gets) in your edit.
Either way, when you have the multiple registrations in place you can happily either 'request' a T[] or IEnumerable<T> and get the full set. If you want to achieve this explicitly (i.e., Service Locator and all it implies - like in you're doing, you can use GetAll to batch them so you're not doing the looping that's implicit in the way you've done it.
Not sure if you've made this connection or if I'm missing something. Either way, I hope it's taught you to stick some code into questions as it speaks > 1000 words :P
It was a problem for me as well. Ninject injects each item of an array instead of the array itself, so you should have a mapping defined for the type of array items. Actually there is no possibility to map the array as a type with the current version of Ninject. The solution is to create a wrapper around the array. Lazy class can be used for example if it suits you. Or you can create your own wrapper.
Since Array implements IReadOnlyList the following works.
// Binding
public sealed class FooModule: NinjectModule
{
public opverride void Load()
{
Bind<IReadOnlyList<IFoo>>().ToConstant(new IFoo[0]);
}
}
// Injection target
public class InjectedClass {
public InjectedClass(IReadOnlyList<IFoo> foos) { ;}
}