简体   繁体   English

Ninject 和静态类 - 如何?

[英]Ninject and static classes - how to?

I have a static class and I need to inject some instances into it.我有一个静态类,我需要向其中注入一些实例。 A static class can have a static constructor but it must be parameterless.静态类可以有静态构造函数,但它必须是无参数的。 So, how am I supposed to inject something into it?那么,我该如何注入一些东西呢?

I do not wish to create a singleton.我不想创建一个单身人士。 I wish to have a static class, and one of its methods operate on an instance that should be injected.我希望有一个静态类,它的方法之一对应该注入的实例进行操作。 Below is an example of the sort of thing I need:下面是我需要的那种东西的例子:

public static class AuthenticationHelper
{
    // Fields.
    private static object _lock = new object();
    private static readonly UserBusiness _userBusiness; // <-- this field needs to be injected.

    // Public properties.
    public static User CurrentUser
    {
        get
        {
            if (IsAuthenticated)
            {
                User user = (User)Context.Session[SessionKeys.CURRENT_USER];

                if (user == null)
                {
                    lock (_lock)
                    {
                        if (user == null)
                        {
                            user = _userBusiness.Find(CurrentUserId);
                            Context.Session[SessionKeys.CURRENT_USER] = user;
                        }
                    }
                }

                return user;
            }

            return null;
        }
    }
    public static int CurrentUserId { get; /* implementation omitted for brevity */ }
    public static bool IsAuthenticated { get; /* implementation omitted for brevity */ }
}

Background info: this is an MVC4 application, so I'm using ninject.mvc3 plugin.背景信息:这是一个 MVC4 应用程序,所以我使用 ninject.mvc3 插件。

PS.: I've seen some questions concerning Ninject and static methods, but none of them seemed to address an issue like this. PS.:我看过一些关于 Ninject 和静态方法的问题,但似乎没有一个能解决这样的问题。

Don't do it.不要这样做。 Don't use a static class that needs dependencies of its own.不要使用需要自身依赖的静态类。 This makes testing harder and other types that depend on this AuthenticationHelper won't be able to include it in their constructor which means they hide the fact that they depend on it.这使得测试更加困难,并且依赖于这个AuthenticationHelper其他类型将无法将它包含在它们的构造函数中,这意味着它们隐藏了它们依赖它的事实。

Instead just do what you would always do: make AuthenticationHelper non-static, implement an IAuthenticationHelper interface on it and inject all dependencies through its public constructor.而只是做你经常做的事情:使AuthenticationHelper非静态,在其上实现IAuthenticationHelper接口并通过其公共构造函数注入所有依赖项。

But if you insist into keeping that class static (which again is a really bad idea), create a static Initialize(UserBusiness userBusiness) method on it, and call this method in the start-up path of your application.但是,如果您坚持保持该类静态(这又是一个非常糟糕的主意),请在其上创建一个静态Initialize(UserBusiness userBusiness)方法,并在应用程序的启动路径中调用此方法。 You can't let your DI container call this static method.你不能让你的 DI 容器调用这个静态方法。 They don't allow because 1. it's a bad idea, and 2. such static method only has to be called once, so letting your container auto-wire this for you doesn't really help.他们不允许,因为 1. 这是个坏主意,2. 这样的静态方法只需要调用一次,所以让你的容器为你自动连接它并没有真正的帮助。

As a side note, the lock is completely useless since you are locking access to a local variable "user" which will not change between the 2 "if (user == null)" lines.附带说明一下,该锁完全没用,因为您正在锁定对局部变量“user”的访问,该变量不会在 2 个“if (user == null)”行之间更改。

Your intention is to lock access to the Context.Session[CURRENT_USER] element, so ..您的意图是锁定对 Context.Session[CURRENT_USER] 元素的访问,因此..

            User user = (User)Context.Session[SessionKeys.CURRENT_USER];

            if (user == null)
            {
                lock (_lock)
                {
                    user = (User)Context.Session[SessionKeys.CURRENT_USER];
                    if (user == null)
                    {
                        user = _userBusiness.Find(CurrentUserId);
                        Context.Session[SessionKeys.CURRENT_USER] = user;
                    }
                }
            }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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