如何注入的UserManager&安培; SignInManager [英] How to inject UserManager & SignInManager

查看:1381
本文介绍了如何注入的UserManager&安培; SignInManager的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我试图找出如何注入的UserManager和SignInManager。我在我的应用程序安装Ninject,我以下列方式使用它:

I am trying to figure out how to inject UserManager and SignInManager. I have installed Ninject in my application and I am using it in the following manner:

请认为这是一个全新的项目。内部Startup.cs我有以下几点:

Please consider this to be a brand new project. Inside Startup.cs I have the following:

public partial class Startup
{
    public void Configuration(IAppBuilder app)
    {
        ConfigureAuth(app);

        app.UseNinjectMiddleware(CreateKernel);
    }

    private static IKernel CreateKernel()
    {
        var kernel = new StandardKernel();
        kernel.Load(Assembly.GetExecutingAssembly());


        return kernel;
    }
}

现在,如果我要创造一些哑类,并尝试基于它的界面,适用于注射了。我已经测试它。我试图搞清楚的是如何将我现在带出以下出来Startup.Auth.cs并注入它。由于没有接口,我可以依靠,我不知道如何做到这一点:

now if I were to create some Dummy class and try to inject it based on its interface that works. I have tested it. What I am trying to figure out is how would I now strip out the following out of Startup.Auth.cs and inject it. Having no interfaces I can rely on, I am not sure how this is done:

app.CreatePerOwinContext(ApplicationDbContext.Create);
app.CreatePerOwinContext<ApplicationUserManager>(ApplicationUserManager.Create);
app.CreatePerOwinContext<ApplicationSignInManager>(ApplicationSignInManager.Create);

只是为了澄清一次,我的问题是:我如何实例ApplicationUserManager和ApplicationSignInManager,在我的控制器参数注入它。下面是我试图注入这个控制器:

Just to clarify one more time, my question is: How do I instantiate ApplicationUserManager and ApplicationSignInManager and inject it in my controller parameters. Here is the controller that I am trying to inject this into:

public AccountController(ApplicationUserManager userManager, ApplicationSignInManager signInManager)
{
    UserManager = userManager;
    SignInManager = signInManager;
}

编辑:

下面是我的尝试:

private static IKernel CreateKernel()
{
    var kernel = new StandardKernel();
    kernel.Load(Assembly.GetExecutingAssembly());

    kernel.Bind<IUserStore<ApplicationUser>>().To<UserStore<ApplicationUser>>();
    kernel.Bind<UserManager<ApplicationUser>>().ToSelf();

    return kernel;
}

但有了这个,我得到空引用错误

But with this I get null reference error

推荐答案

要给出一个确切的答案,说什么我的问题,这里是code和说明:

To give an exact answer to what my question stated, here is the code and instructions:

第1步:
创建自定义用户存储

Step 1: Create custom User Store

public class ApplicationUserStore : UserStore<ApplicationUser>
{
    public ApplicationUserStore(ApplicationDbContext context)
        : base(context)
    {
    }
}

步骤2:
更新ApplicationUserManager和创建方法引入构造移动code

Step 2: Update ApplicationUserManager and move code from Create method into constructor

public class ApplicationUserManager : UserManager<ApplicationUser>
{
    public ApplicationUserManager(IUserStore<ApplicationUser> store, IdentityFactoryOptions<ApplicationUserManager> options)
        : base(store)
    {
        this.UserValidator = new UserValidator<ApplicationUser>(this)
        {
            AllowOnlyAlphanumericUserNames = false,
            RequireUniqueEmail = true
        };

        // Configure validation logic for passwords
        this.PasswordValidator = new PasswordValidator
        {
            RequiredLength = 6,
            RequireNonLetterOrDigit = true,
            RequireDigit = true,
            RequireLowercase = true,
            RequireUppercase = true,
        };

        // Configure user lockout defaults
        this.UserLockoutEnabledByDefault = true;
        this.DefaultAccountLockoutTimeSpan = TimeSpan.FromMinutes(5);
        this.MaxFailedAccessAttemptsBeforeLockout = 5;

        // Register two factor authentication providers. This application uses Phone and Emails as a step of receiving a code for verifying the user
        // You can write your own provider and plug it in here.
        this.RegisterTwoFactorProvider("Phone Code", new PhoneNumberTokenProvider<ApplicationUser>
        {
            MessageFormat = "Your security code is {0}"
        });
        this.RegisterTwoFactorProvider("Email Code", new EmailTokenProvider<ApplicationUser>
        {
            Subject = "Security Code",
            BodyFormat = "Your security code is {0}"
        });
        this.EmailService = new EmailService();
        this.SmsService = new SmsService();
        var dataProtectionProvider = options.DataProtectionProvider;
        if (dataProtectionProvider != null)
        {
            this.UserTokenProvider =
                new DataProtectorTokenProvider<ApplicationUser>(dataProtectionProvider.Create("ASP.NET Identity"));
        }
    }
}

步骤3:
修改Startup.Auth类和注释掉以下code

Step 3: Modify the Startup.Auth class and comment out following code

//app.CreatePerOwinContext(ApplicationDbContext.Create);
//app.CreatePerOwinContext<ApplicationUserManager>(ApplicationUserManager.Create);
//app.CreatePerOwinContext<ApplicationSignInManager>(ApplicationSignInManager.Create);

步骤4:
更新帐户控制(或有问题的任何其他控制器),并​​添加以下构造器

Step 4: Update Account Controller (or any other controller in question) and add the following contructor

public AccountController(ApplicationUserManager userManager, ApplicationSignInManager signInManager, IAuthenticationManager authManager)
{
    _userManager = userManager;
    _signInManager = signInManager;
    _authManager = authManager;
}

第五步:
更新帐户控制器,使属性只retrivable像这样:

Step 5: Update Account Controller and make properties only retrivable as so:

public ApplicationSignInManager SignInManager
{
    get
    {
        return _signInManager;
    }
}

public ApplicationUserManager UserManager
{
    get
    {
        return _userManager;
    }
}

private IAuthenticationManager AuthenticationManager
{
    get
    {
        return _authManager;
    }
}

第六步:
更新Startup.cs

Step 6: Update Startup.cs

public partial class Startup
{
    private IAppBuilder _app;
    public void Configuration(IAppBuilder app)
    {
        ConfigureAuth(app);
        _app = app;
        app.UseNinjectMiddleware(CreateKernel);
    }

    private IKernel CreateKernel()
    {
        var kernel = new StandardKernel();
        kernel.Load(Assembly.GetExecutingAssembly());

        kernel.Bind<ApplicationDbContext>().ToSelf().InRequestScope();
        kernel.Bind<IUserStore<ApplicationUser>>().To<ApplicationUserStore>();
        kernel.Bind<ApplicationUserManager>().ToSelf();
        kernel.Bind<ApplicationSignInManager>().ToSelf();
        kernel.Bind<IAuthenticationManager>().ToMethod(x => HttpContext.Current.GetOwinContext().Authentication);
        kernel.Bind<IDataProtectionProvider>().ToMethod(x => _app.GetDataProtectionProvider());

        return kernel;
    }
}

要进一步扩大这个问题的答案,根据我收到的评论)

To further expand the answer to this question, based on the comments I have recieved):

这些管理者不应该作为注射类作为那么你就没有办成DI。应该怎么做,而不是创造是多接口进一步根据您的需要分离的UserManager组方法。下面是一个例子:

These managers should not be injected as classes as then you are not accomplishing DI. What should be done instead is create multiple interfaces that further separate and group methods of UserManager according to your needs. Here is an example:

public interface IUserManagerSegment
{
    Task<IdentityResult> CreateAsync(ApplicationUser user, string password);
    Task<IdentityResult> CreateAsync(ApplicationUser user);
    Task<IdentityResult> ConfirmEmailAsync(string userId, string token);
    Task<ApplicationUser> FindByNameAsync(string userName);
    Task<bool> IsEmailConfirmedAsync(string userId);
    Task<IdentityResult> ResetPasswordAsync(string userId, string token, string newPassword);
    Task<IList<string>> GetValidTwoFactorProvidersAsync(string userId);
    Task<IdentityResult> AddLoginAsync(string userId, UserLoginInfo login);
    void Dispose(bool disposing);
    void Dispose();
}

以上方法具有一些随机的方法,我选择只是为了说明这一点的列表。与此说,我们不会注入基于接口的方法,像这样的:

The above method has a list of few random methods I chose just to illustrate the point. With this said, we would not inject the method based on the interface such as this:

kernel.Bind<IUserManagerSegment>().To<ApplicationUserManager>();

现在我们的AccountController的构造是这样的:

And now our AccountController constructor would look like this:

public AccountController(IUserManagerSegment userManager, ApplicationSignInManager signInManager, IAuthenticationManager authManager)  
{
    _userManager = userManager;
    _signInManager = signInManager;
    _authManager = authManager;
}

同样的事情应该怎样做才能SignInManager和AuthenticationManager会。

Same thing should be done to SignInManager and AuthenticationManager.

在code以上已经过测试,工作正常。只要确保你有参考下面的DLL的:

The code above has been tested and is working. Just ensure you have reference the following DLL's:

Ninject.dll
Ninject.Web.Common
Ninject.Web.Common.OwinHost
Ninject.Web.Mvc

Ninject.dll Ninject.Web.Common Ninject.Web.Common.OwinHost Ninject.Web.Mvc

这篇关于如何注入的UserManager&安培; SignInManager的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆