I am using the Mediatr in my .Net Core project and I was wondering if the handler's in the Mediatr are singleton's or are the new instances for every Send request; I know the Mediatr is a Singleton' but for the handlers it uses for a command or query, I am not very sure.
I tend to think they would also be singletons; but just wanted to double confirm.
In fact, lifetime of all those things are it's well documented
https://github.com/jbogard/MediatR.Extensions.Microsoft.DependencyInjection/blob/master/README.md
Just for reference: IMediator is transient (not a singleton), IRequestHandler<> concrete implementations is transient and so on so actually it's transient everywhere.
But be aware of using Scoped services with Mediatr handlers, it works not as expected, more like singletons, unless you manually create a scope.
For the handlers, after following the source code, it looks like they are all added as Transient.
https://github.com/jbogard/MediatR.Extensions.Microsoft.DependencyInjection/blob/1519a1048afa585f5c6aef6dbdad7e9459d5a7aa/src/MediatR.Extensions.Microsoft.DependencyInjection/Registration/ServiceRegistrar.cs#L57
services.AddTransient(#interface, type);
For the IMediator itself, it looks like it is lifetime by default :
https://github.com/jbogard/MediatR.Extensions.Microsoft.DependencyInjection/blob/1519a1048afa585f5c6aef6dbdad7e9459d5a7aa/src/MediatR.Extensions.Microsoft.DependencyInjection/Registration/ServiceRegistrar.cs#L223
services.Add(new ServiceDescriptor(typeof(IMediator), serviceConfiguration.MediatorImplementationType, serviceConfiguration.Lifetime));
Note that the service configuration is a configuration object that unless somehow you change it along it's default path, will be set to transient too :
public MediatRServiceConfiguration()
{
MediatorImplementationType = typeof(Mediator);
Lifetime = ServiceLifetime.Transient;
}
Using core you can manually register your handlers and use whatever scope you want. So for example:
services.AddScoped<IPipelineBehavior<MyCommand>, MyHandler>();
We actually wrap Mediatr so we can add various bits and bobs so it ends up being a registration extension like this (CommandContect/QueryContext holds various stuff we use all the time and ExecutionResponse is a standard response so we can have standard post handlers that know what they are getting):
public static IServiceCollection AddCommandHandler<THandler, TCommand>(this IServiceCollection services)
where THandler : class, IPipelineBehavior<CommandContext<TCommand>, ExecutionResponse>
where TCommand : ICommand
{
services.AddScoped<IPipelineBehavior<CommandContext<TCommand>, ExecutionResponse>, THandler>();
return services;
}
Which is used like this:
services.AddCommandHandler<MyHandler, MyCommand>();
We have similar for queries (AddQueryHandler<.....)
Hope that helps
Related
I'm trying to get an understanding of which concrete types are providing the implementations of interfaces in an IOC (dependency injection) container. My implementation works fine when there are no delegates involved. However, I'm having trouble when a delegate method is passed as the type factory, as I can't get Mono.Cecil to give me the concrete type or a method reference to the factory back. I'm specifically in this case trying to build a component that can work with the IServiceCollection container for .Net ASP.Net REST APIs. I've created a 'minimised' set of code below to make it easy to explain the problem.
Consider the following C# code:
interface IServiceProvider {}
interface IServiceCollection {}
class ServicesCollection : IServiceCollection {}
interface IMongoDBContext {}
class MongoDBContext : IMongoDBContext
{
public MongoDBContext(string configName) {}
}
static class Extensions
{
public static IServiceCollection AddSingleton<TService>(this IServiceCollection services, Func<IServiceProvider, TService> implementationFactory) where TService : class
{
return null;
}
}
class Foo
{
void Bar()
{
IServiceCollection services = new ServicesCollection();
services.AddSingleton<IMongoDBContext>(s => new MongoDBContext("mongodbConfig"));
}
}
When successfully locating the 'services.AddSingleton' as a MethodReference, I'm unable to see any reference to the MongoDBContext class, or its constructor. When printing all the instructions .ToString() I also cannot seem to see anything in the IL - I do see the numbered parameter as !!0, but that doesn't help if I can't resolve it to a type or to the factory method.
Does anyone have any ideas on how to solve this?
Most likely your code is looking in the wrong place.
C# compiler will try to cache the conversion of lambda expression -> delegate.
if you look in sharplab.io you'll see that the compiler is emitting an inner class '<>c' inside your Foo class and in that class it emits the method '<Bar>b__0_0' that will be passed as the delegate (see opcode ldftn).
I don't think there's an easy, non fragile way to find that method.
That said, one option would be to:
Find the AddSingleton() method call
From there start going back to the previous instructions trying to identify which one is pushing the value consumed in 1 (the safest way to do that would be to consider how each instruction you are visiting changes the stack). In the code I've linked, it would be IL_0021 (a dup) of Bar() method.
From there, do something similar to 2, but now looking for the instruction that pushes the method reference (a ldftn) used by the ctor of Func<T, R>; in the code linked, it would be IL_0016.
Now you can inspect the body (in the code linked, Foo/'<>c'::'<Bar>b__0_0')
Note that this implementation has some holes though; for instance, if you call AddSingleton() with a variable/parameter/field as I've done (services.AddSingleton(_func);) you'll need to chase the initialization of that to find the referenced method.
Interestingly, at some point Cecil project did support flow analysis (https://github.com/mono/cecil-old/tree/master/flowanalysis).
If you have access to the source code, I think it would be easier to use Roslyn to analyze it (instead of analyzing the assembly).
Still exploring the new ASP.NET MVC5, now with build in DI!
No Problem so far, I can just inject my Handlers (I don't like the Term Service, since this defines to me a Platform-Neutral Interface):
// This method gets called by the runtime. Use this method to add services to the container.
public void ConfigureServices(IServiceCollection services)
{
services.AddApplicationInsightsTelemetry(Configuration);
services.Configure<Model.Meta.AppSettings>(Configuration.GetSection("AppSettings"));
services.AddSingleton(typeof(Logic.UserEndPointConfigurationHandler));
services.AddSingleton(typeof(Logic.NetworkHandler));
services.AddMvc();
}
Works fine, also the strongly typed Configuration-Object "AppSettings" works perfectly fine.
Also the Injection in the Controllers works as well.
But now my collaps: I seperated my DataAccess from the Handlers, and obviously I'd like to inject them as well:
public class UserEndPointConfigurationHandler
{
private readonly DataAccess.UserEndPointAccess _access;
public UserEndPointConfigurationHandler(DataAccess.UserEndPointAccess access)
{
_access = access;
}
But bam, UserEndPointAccess can't be resolved. So it seems like even I directly request to DI an Class with a Parameterless-Constructor, I need to register that. For this case, sure I should Interface and register them, but what does that mean for internal helper classes I also inject?
According to the Docs: http://docs.asp.net/en/latest/fundamentals/dependency-injection.html#recommendations and also the examples I found, all people in the world only seem to communicate between Controllers and some Repositories. No Business-Layer and no Classes on different Abstraction-Levels in Assemblies.
Is the Microsoft DI approach something totally differnt than the good ol' Unity one, where I can really decouple as fine granular as I'd like to?
Thanks in advance.
Matthias
Edit #Nightowl: I add my answer here, since it's a bit longer.
First of all, Unity does automatically create Instances, if I request a conecrete Type. This allows me to inject Types I register and Types, like Helper classes etc. I don't need to. This combination allows me to use DI everywhere.
Also in your Example I'd need to know the DataAcces in the WebGui, which is quite thight coupled. Well, I know there are solutions for this via Reflection, but I hoped Microsoft did something in this Topic, but probably that'd mean to big of a change.
Also allows Unity to store Instances or Instructions how to create them, another huge feature, which is missing at the moment.
Probably I'm just to spoiled, what refined DI-Libraries do, probably they also do to much, but at the moment the Microsoft-Implementation is just a huge downgrade according to my Information.
MVC Core follows the the composition root pattern, which is where object graphs are created based off of a set of instructions to instantiate them. I think you are misinterpreting what the IServiceCollection is for. It does not store instances, it stores instructions on how to create instances. The instances aren't actually created until a constructor somewhere in the object graph requests one as a constructor parameter.
So, in short the reason why your service (which you call UserEndPointAccess) is not being instantiated when you request it is because you have not configured the IServiceCollection with instructions on how to create it.
// This method gets called by the runtime. Use this method to add services to the container.
public void ConfigureServices(IServiceCollection services)
{
services.AddApplicationInsightsTelemetry(Configuration);
services.Configure<Model.Meta.AppSettings>(Configuration.GetSection("AppSettings"));
services.AddSingleton(typeof(Logic.UserEndPointConfigurationHandler));
services.AddSingleton(typeof(Logic.NetworkHandler));
// Need a way to instantiate UserEndPointAccess via DI.
services.AddSingleton(typeof(DataAccess.UserEndPointAccess));
services.AddMvc();
}
So it seems like even I directly request to DI an Class with a Parameterless-Constructor, I need to register that.
If you are doing DI correctly, each service class will only have a single constructor. If you have more than one it is known as the bastard injection anti-pattern, which essentially means you are tightly coupling your class definition to other classes by adding references to them as foreign defaults.
And yes, you need to register every type you require (that is not part of MVC's default registration). It is like that in Unity as well.
I have implemented IAuthenticationFilter to create a custom one. in the constructor I use structureMap to get instance of my IUnitOfWork. this authentication logic is to check user status in the database and ....
IUnitOfWork uow;
public CustomAuthenticatationAttribute()
{
this.uow = ObjectFactory.GetInstance<IUnitOfWork>();
}
I have configured structureMap to serve IUnitOfWork HttpContextScoped.
x.For<IUnitOfWork>().HttpContextScoped().Use(() => new MyDbContext());
but then something strange happened. I deleted the user in one action, but when the AuthenticationFilter is executed on another action, the instance of unitOfWork still returns the user ! I searched the web for hours and I come to this :
Are ActionFilterAttributes reused across threads? How does that work?
in short , it says that Filters are cached and used across requests !
Now I'm confused . how to deal with this ? shall I give up using unitOfWork and get back to using(var context = ....) ? or there is a correct way of using unitOfWork inside Filters .
I found a solution here
https://gist.github.com/ivanra/9019273
It replaces the DefaultFilterProvider and I prefer to avoid that if possible.
The solution you found with suppressing caching in the FilterProvider is actually the same solution that the MVC integration libraries for both Autofac and Simple Injector use.
But the caching behavior of attributes is just one of the many reasons why doing dependency injection in attributes is actually a bad idea.
The best solution is IMO to move to passive attributes if you can, or at least encapsulate the attributes logic and its dependencies into a component and don't do anything more than resolving and executing that component in the OnActionExecuting method. For instance:
public class CustomAuthenticatationAttribute : ActionFilterAttribute
{
public override void OnActionExecuting(ActionExecutingContext context)
{
var action =
ObjectFactory.GetInstance<IActionFilter<CustomAuthenticatationAttribute>>();
action.OnActionExecuting(this, context);
}
}
For ASP.NET Web API, I've been working on my own implementation of IHttpControllerActivator and am left wondering when (or why?) to use the HttpRequestMessage extension method "RegisterForDispose".
I see examples like this, and I can see the relevance in it, since IHttpController doesn't inherit IDisposable, and an implementation of IHttpController doesn't guarantee its own dispose logic.
public IHttpController Create(HttpRequestMessage request, HttpControllerDescriptor controllerDescriptor, Type controllerType)
{
var controller = (IHttpController) _kernel.Get(controllerType);
request.RegisterForDispose( new Release(()=> _kernel.Release(controller)));
return controller;
}
But then I see something like this and begin to wonder:
public IHttpController Create(
HttpRequestMessage request,
HttpControllerDescriptor controllerDescriptor,
Type controllerType)
{
if (controllerType == typeof(RootController))
{
var disposableQuery = new DisposableStatusQuery();
request.RegisterForDispose(disposableQuery);
return new RootController(disposableQuery);
}
return null;
}
In this instance RootController isn't registered for disposal here, presumably because its an ApiController or MVC Controller? - And thus will dispose itself.
The instance of DisposableStatusQuery is registered for disposal since it's a disposable object, but why couldn't the controller dispose of the instance itself? RootController has knowledge of disposableQuery (or rather, it's interface or abstract base), so would know it's disposable.
When would I actually need to use HttpRequestMessage.RegisterForDispose?
One scenario I've found it useful for: for a custom ActionFilter.
Because the Attribute is cached/re-used, items within the Attribute shouldn't rely on the controller to be disposed of (to my understanding - and probably with caveats)... so in order to create a custom attribute which isn't tied to a particular controller type/implementation, you can use this technique to clean up your stuff. In my case, it's for an ambient DbContextScope attribute.
RegisterForDispose it's a hook that will be called when the request is disposed. This is often used along with "some" of the dependency injection containers.
For instance, some containers (like Castle.Windsor) by default will track all dependencies that they resolve. This is according to Windsor ReleasePolicy LifecycledComponentsReleasePolicy which states that it will keep track of all components that were created. In other words your garbage collector will not be able to cleanup if your container still tracks your component. Which will result into memory leaks.
So for example when you define your own IHttpControllerActivator to use it with a dependency injection container it is in order to resolve the concrete controller and all its dependencies. At the end of the request you need to release all the created dependencies by the container otherwise you will end with a big memory leak. You have this opportunity doing it with RegisterForDispose
I use RegisterForDispose with the DI container's. Based on Blog post I have implemented to dispose the container(Nested Container) after each request so that it clears all the objects which i has created.
One may want to hook code around the life cycle of a request that (1) has little to do with controllers and (2) does not subclass the request type.
I would imagine the idiomatic form of such code takes the shape of extension methods on HttpRequestMessage, for example. If the code allocates disposable resources, it would need to hook the disposal code to something. I'm not too familiar with the various extension points of the ASP.NET pipeline, but I suppose hooking code just to dispose of resources at the end of the request processing stage was common enough to justify a dedicated registration mechanism for disposable resources (as opposed to more generally subscribing code to be executed).
Since you're asking, I found a nice example scenario in this sample. Here, an Entity Framework context is set as a property of the request, and must be disposed of properly. While this property is intended to be used by controllers, they're not specific to any controller or controller super-class, so in my opinion this is a very sensible design choice. If you're curious why, this is because these requests are "OData batch requests" and controller actions will be invoked multiple times over the lifetime of each request (once per "operation"). Certain operations are grouped into atomic "changesets" that must be wrapped in transactions at a higher-level than controllers (a dedicated mechanism is used: an ODataBatchHandler, so that the controllers themselves are oblivious to this). Hence, controllers alone are not enough, as one cannot have them dispose of the context themselves in this scenario.
Hope this helps.
I am trying to design an application in 3 layers :
1) Data access layer
2) business layer
3) UI
I try to keep classes decoupled so on the business layer I have created interfaces for the Data access classes like this :
public interface ICountryRepository:IRepository
{
Country GetCountry(int ID);
int CreateCountry(Country obj);
Boolean UpdateCountry(Country obj);
Boolean DeleteCountry(Country obj);
...
...
}
and i pass the interface as param to the service constructor :
public CountryService(ICountryRepository repository,ILanguageRepository lang_repository)
{
....
}
But on the CountryService for example I need to load the current user and his permissions so I can check if the operation can be applied :
public Country GetCountry(int ID)
{
if securityService.UserHasPermission(currentUser, GetPermission("CanGetCountry"))
{
return repository.GetCountry(ID);
}
else
{
Throw(New SecurityException("No permissions for that operation ...."))
}
}
That means I have to instantiate the SecurityDataAccess object and pass it to the constructor of the SecurityService on my business layer assembly which I try to avoid for keeping objects decoupled. Right now I even don't have a reference to any DataAccess assembly on my business assembly.
I am thinking of using an IoC container here. Using external configuration I could get the right class/assembly from a config file. But I am not sure that is the right solution because it is said that IoC containers should be used in one place to keep things simple and it should be the top level assembly (the UI assembly) most of the time.
Anybody has a suggestion for solving this problem ?
Why not add the security service into the constructor of the Country service? That way the IOC Container could resolve the dependency and inject the security if it is needed. That mean the IOC Container would take care of constructing your CountryService object. And you would use the container to get all Services.
Another option could be to "normalize" your repository a bit...
Trim it down to it only has 4-5 basic functions that are identical for all repositories, then use generics to make them all look alike, so no
UpdateCountry(...)
but
Update(T object)
Something like this:
http://codebetter.com/blogs/gregyoung/archive/2009/01/16/ddd-the-generic-repository.aspx
Then you can use a Chain of reponsibilty pattern to place your security code before the DB Code ( http://en.wikipedia.org/wiki/Chain-of-responsibility_pattern )
So you could have a SecurityChecker that validates access, throws an exception if invalid, or passes down the request in the next link in the chain (You can also add a logging dynamically that way, or timing or whatever)
Do you need to implement security in the Data Access layer? If you move your security service to the business layer as Heiko suggests. In other words, perform security in the business layer and you avoid the IoC issue altogether.
This may be off-beam, apologies if it is, I'm a lurking Java EE programmer. It seems to me that authorisation is of methods is better addressed in the infrastructure, declaratively.
This article appears to suggest that .Net, like Java EE offers a facility to control access declaratively. Does this approach work for you?