这是我的设置:
public class ApplicationUser : IdentityUser<Guid>
{
}
public class ApplicationRole : IdentityRole<Guid>
{
}
public class ApplicationUserLogin : IdentityUserLogin<Guid>
{
}
public class ApplicationUserClaim : IdentityUserClaim<Guid>
{
}
public class ApplicationRoleClaim : IdentityRoleClaim<Guid>
{
}
这是我的 UserStore 的定义
Here is the definition of my UserStore
public class ApplicationUserStore : UserStore<ApplicationUser, ApplicationRole, MyContext, Guid>
{
public ApplicationUserStore(MyContext context, IdentityErrorDescriber describer = null)
: base(context, describer)
{
}
}
这是我的 UserManager 的定义
Here is the definition of my UserManager
public class ApplicationUserManager : UserManager<ApplicationUser>
{
public ApplicationUserManager(IUserStore<ApplicationUser> store, IOptions<IdentityOptions> optionsAccessor,
IPasswordHasher<ApplicationUser> passwordHasher, IEnumerable<IUserValidator<ApplicationUser>> userValidators,
IEnumerable<IPasswordValidator<ApplicationUser>> passwordValidators, ILookupNormalizer keyNormalizer,
IdentityErrorDescriber errors, IEnumerable<IUserTokenProvider<ApplicationUser>> tokenProviders,
ILoggerFactory logger, IHttpContextAccessor contextAccessor)
: base(
store, optionsAccessor, passwordHasher, userValidators, passwordValidators, keyNormalizer, errors,
tokenProviders, logger, contextAccessor)
{
}
}
这是我的 DbContext 的定义:
Here is the definition of my DbContext:
public class MyContext : IdentityDbContext<ApplicationUser, ApplicationRole, Guid>
{
protected override void OnModelCreating(ModelBuilder builder)
{
base.OnModelCreating(builder);
}
}
这是我的 Startup.cs
And here is my Startup.cs
public IServiceProvider ConfigureServices(IServiceCollection services)
{
services.AddMvc();
services.AddEntityFramework()
.AddSqlServer()
.AddDbContext<MyContext>(options => options.UseSqlServer(Configuration.Get("Data:DbConnection")));
services.AddIdentity<ApplicationUser, ApplicationRole>()
.AddEntityFrameworkStores<MyContext, Guid>()
.AddUserStore<ApplicationUserStore>()
.AddRoleStore<ApplicationRoleStore>()
.AddUserManager<ApplicationUserManager>()
.AddRoleManager<ApplicationRoleManager>()
.AddDefaultTokenProviders();
var builder = new ContainerBuilder();
builder.Populate(services);
var container = builder.Build();
return container.Resolve<IServiceProvider>();
}
这个构造函数的依赖会起作用:
The dependency of this constructor will work:
public AccountController(UserManager<ApplicationUser> userManager, SignInManager<ApplicationUser> signInManager)
这个不会:
public AccountController(ApplicationUserManager userManager, SignInManager<ApplicationUser> signInManager)
有人知道我做错了什么吗?
Anyone has an idea on what I'm doing wrong?
一般来说,DI 是为接口驱动开发而设计的;.AddUserManager<ApplicationUserManager>()
指定实现 UserManager<>
,而不是服务接口.这意味着它仍然希望您获得 UserManager
并仅以这种方式使用它;它会给你一个 ApplicationUserManager
.
DI in general is intended for interface-driven development; .AddUserManager<ApplicationUserManager>()
specifies an implementation UserManager<>
, not the service interface. That means that it's still expecting you to get UserManager<ApplicationUser>
and only use it that way; it'll give you an ApplicationUserManager
.
我假设您想在 ApplicationUserManager
上使用其他方法.如果不是, 按照它的工作方式使用依赖构造器,享受接口驱动的开发.如果是,你有3个选择:
I'm assuming that you have additional methods you want to use on your ApplicationUserManager
. If not, just use the dependency constructor the way it works and enjoy the interface-driven development. If so, you have 3 options:
通过组合而不是继承使用扩展. 与其从 UserManager<>
继承,不如将 ApplicationUserManager
编写为包装类;您可以将其包含在构造函数中.这应该为您提供 ApplicationUserManager
中所需的所有功能.
Use extension via composition rather than inheritance. Rather than inheriting from UserManager<>
, write ApplicationUserManager
as a wrapper class; you can include it in the constructor. This should give you all the functionality you need inside of the ApplicationUserManager
.
您自己将其按原样添加到 DI 框架中. 这并不像听起来那么难,因为 UserManager<>
没有真正的状态本身:
Add it as-is to the DI framework yourself. This isn't as difficult as it sounds, since the UserManager<>
has no real state itself:
services.AddScoped<ApplicationUserManager>();
这里的缺点是您实际上将有两个 UserManager<>
对象用于用户的范围;结果可能会导致一些效率低下.从当前代码的状态来看,我认为不是.
The disadvantage here is that you'll actually have two UserManager<>
objects for the user's scope; there could be some inefficiencies as a result. From the state of the current code, I don't think it is.
将其编写为扩展方法.如果您有许多依赖项,而不仅仅是 UserManager<>
的基本功能,这可能真的是复杂.
Write it as extension methods. If you have a number of dependencies and not just the UserManager<>
's base functionality, this could be really complex.
这篇关于如何注册自定义 UserStore &DI 中的用户管理器的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持跟版网!