如何将 Ninject 与 ActionResults 结合使用,同时使控制器与 IoC 框架无关?

发布于 2024-09-30 08:45:41 字数 967 浏览 0 评论 0原文

我见过的几乎所有 Ninject 示例都解释了如何将其与 ASP.NET MVC 一起使用,它将自动将依赖项注入到控制器中。我该如何手动使用 Ninject 呢?假设我有一个自定义 ActionResult:

public class JsonResult : ActionResult
{
    [Inject] public ISerializer Serializer { get; set; }

    public JsonResult(object objectToSerialize)
    {
        // do something here
    }

    // more code that uses Serializer
}

然后在我的控制器中,我在如下方法中使用 JsonResult:

public ActionResult Get(int id)
{
    var someObject = repo.GetObject(id);
    return new JsonResult(someObject);
}

如您所见,我自己实例化该对象,这回避了 Ninject 的注入,并且Serializer 将为 null。但是,按照以下方式进行操作对我来说似乎不太正确:

public ActionResult Get(int id)
{
    var someObject = repo.GetObject(id);
    return IoC.Kernel.Get<JsonResult>(someObject);
}

因为现在控制器中不仅依赖于 Ninject,而且我还必须在静态类/单例中公开 Ninject 内核,并确保依赖的对象注入时仅通过内核创建。

有没有办法以某种方式配置 Ninject 来注入依赖项而不依赖于暴露内核?如果可能的话,我希望能够使用 new 关键字。

Nearly all of the Ninject examples I've seen explain how to use it with ASP.NET MVC, which will automatically inject dependencies into controllers. How would I use Ninject manually though? Let's say I have a custom ActionResult:

public class JsonResult : ActionResult
{
    [Inject] public ISerializer Serializer { get; set; }

    public JsonResult(object objectToSerialize)
    {
        // do something here
    }

    // more code that uses Serializer
}

Then in my controller, I'm using JsonResult in a method like this:

public ActionResult Get(int id)
{
    var someObject = repo.GetObject(id);
    return new JsonResult(someObject);
}

As you can see, I'm instantiating the object myself, which sidesteps Ninject's injection, and Serializer will be null. However, doing it the following way doesn't seem quite right to me:

public ActionResult Get(int id)
{
    var someObject = repo.GetObject(id);
    return IoC.Kernel.Get<JsonResult>(someObject);
}

Because now there's not only a dependency on Ninject in the controller, but I also have to expose the Ninject kernel in a static class/singleton and ensure that objects that rely on injection are only created via kernel.

Is there a way to somehow configure Ninject to inject the dependency without relying on exposing the kernel? I'd like to be able to use the new keyword if at all possible.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

墨小墨 2024-10-07 08:45:41

使用注入内核的工厂:例如,

public class ResultFactory : IResultFactory
{
    public ResultFactory(IKernel kernel)
    {
        this.kernel = kernel;
    }

    public JsonResult CreateJsonResult(object obj)
    {
        var result = this.kernel.Get<JsonResult>();
        result.ObjectToSerialize = obj;
        return result;
    }
}

将此工厂注入控制器并使用它来创建操作结果。

Use a factory that gets the kernel injected: E.g.

public class ResultFactory : IResultFactory
{
    public ResultFactory(IKernel kernel)
    {
        this.kernel = kernel;
    }

    public JsonResult CreateJsonResult(object obj)
    {
        var result = this.kernel.Get<JsonResult>();
        result.ObjectToSerialize = obj;
        return result;
    }
}

Inject this factory into the controller and use it to create your action results.

心凉怎暖 2024-10-07 08:45:41

我认为您应该将您的 JsonResult 翻过来:

public class JsonResult : ActionResult
{
    public ISerializer Serializer { get; private set; }

    public object ObjectToSerialize { get; set; }

    public JsonResult(ISerializer serializer)
    {
        this.Serializer = serializer;
    }

    // more code that uses Serializer
}

这样您就可以使用容器检索 JsonResult ,如下所示:

public ActionResult Get(int id)
{
    var result = IoC.Kernel.Get<JsonResult>();

    result.ObjectToSerialize = repo.GetObject(id);

    return result;
}

更改 JsonResult 的签名还允许 Ninject 自动创建实例。因此,您可以让 Ninject 自动将其作为依赖项注入到您的控制器中:

public MyController(JsonResult result)
{
    this.result = result;
}

public ActionResult Get(int id)
{
    this.result.ObjectToSerialize = repo.GetObject(id);

    return this.result;
}

I think you should turn your JsonResult inside out:

public class JsonResult : ActionResult
{
    public ISerializer Serializer { get; private set; }

    public object ObjectToSerialize { get; set; }

    public JsonResult(ISerializer serializer)
    {
        this.Serializer = serializer;
    }

    // more code that uses Serializer
}

This way you can retrieve the JsonResult with the container like this:

public ActionResult Get(int id)
{
    var result = IoC.Kernel.Get<JsonResult>();

    result.ObjectToSerialize = repo.GetObject(id);

    return result;
}

Changing the signature of the JsonResult also enables Ninject to create an instance automatically. Because of this you can let Ninject automatically inject it as dependency into your controller:

public MyController(JsonResult result)
{
    this.result = result;
}

public ActionResult Get(int id)
{
    this.result.ObjectToSerialize = repo.GetObject(id);

    return this.result;
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文