NInject Custom context

旧街凉风 提交于 2019-12-12 01:57:53

问题


I'll expose what I'm doing now, and later, what I'd like to do using NInject.

Classes:

  1. Kernel,
  2. ApiClient
  3. IIdentity

Kernel exposes several methods as:

object method(IIdentity identity)
-----------------------
public List<Domain.Channel> getChannels(Domain.Identity.IIdentity identity) {...}

Kernel contains several identities stored, and according each context I need to do a thing or another. In this case, my context is inside the method and the context key is identity parameter value. According this one, I need to get an instance of ApiClient.

Actually, I'm doing this using a Dictionary property of Kernel class:

 private Dictionary<Domain.Identity.IIdentity, LEST.Client.ApiClient> lests;

And then I initialize.

 foreach (Domain.Identity.IIdentity identity in this.identities)
 {
     LEST.Client.ApiClient lest = new LEST.Client.ApiClient();
     lest.configure(identity.ClientId, identity.Username, identity.Password);

     this.lests.Add(identity, lest);
 }

So, when I need to get a concrete ApiClient object according an identity:

public List<Domain.Channel> getChannels(Domain.Identity.IIdentity identity)
{
    LEST.Client.ApiClient current_lest;
    this.lests.TryGetValue(identity, out current_lest);

    if (current_lest != null)
    {
        ...        
    }

I'd like to do it using NInject. I've created a module in order to create the bindings to itselfs. The problem is that I've no idea how to create a custom context like this.

I'll appreciate a lot your help.

Thanks for all.

EDIT

I've abstracted a basic Core class that summarizes my explanation.

public class Core
{
    private IList<IIdentity> identities;
    private Ninject.IKernel kernel;

    public Core()
    {
        this.identities = new List<IIdentity>();
    }

    public void initialize()
    {
        this.kernel = new Ninject.StandardKernel(new LestModule());
    }

    public void openSession(IIdentity identity)
    {
        ApiClient client = this.kernel.Get<ApiClient>();
    }

    public void doSomething(IIdentity identity)
    {
        ApiClient client = this.kernel.Get<ApiClient>();
        client...
    }

    public void closeSession(IIdentity identity)
    {
        ApiClient client = this.kernel.Get<ApiClient>();
        this.kernel.Release(client);
    }
}

And the module is:

public class LestModule : Ninject.Modules.NinjectModule
{
    public override void Load()
    {
        this.Bind<ApiClient>().ToProvider(new CustomProvider());
        this.Bind<IIdentity>().To<Identity>();
    }
}

public class CustomProvider : IProvider<ApiClient>
{

    public object Create(IContext context)
    {
        //context data???
        // How to obtain current IIdentity on here?
        object d = context;
        return new ApiClient("", "", "");
    }

    public System.Type Type
    {
        get { return typeof(ApiClient); }
    }
}

And the abstraction of ApiClient

public class ApiClient
{

    private string username;

    public string Username
    {
        get { return username; }
        set { username = value; }
    }

    private string client_id;

    public string ClientId
    {
        get { return client_id; }
        set { client_id = value; }
    }

    private string passwd;

    public string Passwd
    {
        get { return passwd; }
        set { passwd = value; }
    }


    public ApiClient(string client_id, string username, string password)
    {
        this.client_id = client_id;
        this.username = username;
        this.passwd = password;
    }
}

So, I'd like that:

  1. In openSession: Create a ApiClient instance (this.kernel.Get) initializing the instance according the IIdentity param of this method.
  2. In doSomething: Get a ApiClient instance according the IIdentity param of this method.
  3. In closeSession: Realise the instance according the IIdentity param of this method.

回答1:


I've implemented this.

It's working now.

public class LestModule : Ninject.Modules.NinjectModule
{

    public override void Load()
    {
        this.Bind<LEST.Client.ApiClient>().ToProvider<LEST.Client.ApiClient>(new ApiClientProvider());
    }

}

public class ApiClientProvider : Ninject.Activation.IProvider<LEST.Client.ApiClient>
{

    private System.Collections.Generic.Dictionary<Domain.Identity.LESTIdentity, LEST.Client.ApiClient> lests;

    public ApiClientProvider()
    {
        this.lests = new System.Collections.Generic.Dictionary<Domain.Identity.LESTIdentity, LEST.Client.ApiClient>();
    }

    public object Create(Ninject.Activation.IContext context)
    {
        Ninject.Parameters.IParameter identity_parameter = context.Parameters.FirstOrDefault(p => p.Name == "identity");
        Domain.Identity.LESTIdentity identity = (Domain.Identity.LESTIdentity)identity_parameter.GetValue(context, null);

        LEST.Client.ApiClient current_client = null;
        this.lests.TryGetValue(identity, out current_client);
        if (current_client == null)
        {
            current_client = new LEST.Client.ApiClient();
            current_client.configure(...);

            this.lests.Add(identity, current_client);
        }

        return current_client;
    }

    ...
}

In order to get the instance according to the identity:

public void createChannel(Domain.Identity.ClientIdentity client_identity, Domain.Identity.UserIdentity user_identity, Domain.Channel channel)
    {
        LEST.Client.ApiClient client = NinjectServiceLocator.Instance.Kernel.Get<LEST.Client.ApiClient>(new Ninject.Parameters.Parameter("identity", new Domain.Identity.LESTIdentity(user_identity.Id, user_identity.Name, client_identity.Id, client_identity.Name), true));
        client.ChannelsApiP.Create(AutoMapper.Mapper.Map<Domain.Channel, LEST.Model.ChannelDTO>(channel));
    }

What do you thing about?



来源:https://stackoverflow.com/questions/31476018/ninject-custom-context

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!