简体   繁体   中英

simple injector - inject into IHttpHandler

I'm trying to embed SimpleInjector in my WCF project (I've followed the instructions here ). Till now everything went well except from IHttpHandler issue: the current implementation uses IHttpHandler which in turn uses MyServiceWrapper static instance:

public class IsAliveHandler : IHttpHandler
{
    private const string SERVER_ERROR = "Bad";
    private const string SERVER_OK = "OK";

    public void ProcessRequest(HttpContext context)
    {
        var quoteSucceeded = false;
        var isLastLoginSucceeded = MyServiceWrapperContainer.Manager.IsLastLoginSucceeded;
//More logic here ...
    }
}

Now, since I moved my application to use the SimpleInjector DI mechanism I can't use such a static access since I want to use the same instance as held by the DI container. constructor injection here gets exception:

[MissingMethodException: Constructor on type '***.Applications.MyServiceWrapperService.KeepAliveHandler.IsAliveHandler' not found.]

Is there a way to use container in such scenario? Are there alternatives?

Generally, I can understand that such problem is smell of using state, but currently this is the requirement.

Your IsAliveHandler can't have any constructor arguments (this is a constraint of your application framework).

Instead, you should make your IsAliveHandler a Humble Object and consider it to be part of your Composition Root .

This means that you extract all interesting logic out of the IsAliveHandler (eg into an IsAliveService ) and change IsAliveHandler to something as follows:

public class IsAliveHandler : IHttpHandler
{
    public void ProcessRequest(HttpContext context)
    {
        Bootstrapper.Container.GetInstance<IsAliveService>().Process(context);
    }
}

In other words, the only thing you let the IsAliveHandler do is to request the service from the DI Container and invoke the appropriate method on that resolved service.

Do note that IsAliveHandler should stay completely stateless: the resolve IsAliveService should nowhere be stored. You should leave it up to the DI Container to provide you with the correct instance.

In case this operation runs outside the context of a Simple Injector Scope , you might to wrap the operation inside such a Scope :

public void ProcessRequest(HttpContext context)
{
    using (AsyncScopedLifestyle.BeginScope(Bootstrapper.Container))
    {
        Bootstrapper.Container.GetInstance<IsAliveService>().Process(context);
    }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM