c# - 如何在 DI 中注册自定义 UserManager 等 - ASP.NET Core 2.1
问题描述
我需要创建自己的类来处理 EF Core 2.1 中的身份。我有以下那些,但是当想要 inbocar 控制器的方法时,我收到以下错误
尝试激活“Sample.API.Models.Identity.Managers.ApplicationUserManager”时无法解决“Sample.API.Models.Identity.Stores.ApplicationUserStore”类型的服务。
public void ConfigureServices(IServiceCollection servicesCollection)
{
servicesCollection.AddDbContext<MyIndentityContext>(currentOptions =>
currentOptions.UseSqlServer(Configuration.GetConnectionString("DefaultConnection")));
servicesCollection.AddIdentity<ApplicationUser, ApplicationRole>()
.AddEntityFrameworkStores<MyIndentityContext>()
.AddRoleStore<ApplicationRoleStore>()
.AddUserStore<ApplicationUserStore>()
.AddUserManager<ApplicationUserManager>()
.AddRoleManager<ApplicationRoleManager>()
.AddSignInManager<ApplicationSignInManager>()
.AddDefaultTokenProviders();
servicesCollection.AddTransient<UserManager<ApplicationUser>, ApplicationUserManager>();
servicesCollection.AddTransient<SignInManager<ApplicationUser>, ApplicationSignInManager>();
servicesCollection.AddTransient<RoleManager<ApplicationRole>, ApplicationRoleManager>();
servicesCollection.AddTransient<IUserStore<ApplicationUser>, ApplicationUserStore>();
servicesCollection.AddTransient<IRoleStore<ApplicationRole>, ApplicationRoleStore>();
...
...
...
}
public class MyIndentityContext : IdentityDbContext<ApplicationUser, ApplicationRole, string>
{
private readonly IConfiguration _configuration;
private readonly IHttpContextAccessor _httpContextAccessor;
public MyIndentityContext(DbContextOptions dbContextOptions, IHttpContextAccessor httpContextAccessor,
IConfiguration configuration)
: base(dbContextOptions)
{
_configuration = configuration;
_httpContextAccessor = httpContextAccessor;
}
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
modelBuilder.HasDefaultSchema("Sample.API");
}
}
public class ApplicationRoleManager : RoleManager<ApplicationRole>
{
public ApplicationRoleManager(ApplicationRoleStore roleStore,
IEnumerable<IRoleValidator<ApplicationRole>> roleValidators, ILookupNormalizer keyNormalizer,
IdentityErrorDescriber errors, ILogger<ApplicationRoleManager> logger) : base(roleStore,
roleValidators,
keyNormalizer, errors, logger)
{
}
}
public class ApplicationSignInManager : SignInManager<ApplicationUser>
{
public ApplicationSignInManager(ApplicationUserManager userManager, IHttpContextAccessor contextAccessor,
IUserClaimsPrincipalFactory<ApplicationUser> claimsFactory, IOptions<IdentityOptions> optionsAccessor,
ILogger<ApplicationSignInManager> logger, IAuthenticationSchemeProvider schemes) : base(userManager,
contextAccessor, claimsFactory, optionsAccessor, logger, schemes)
{
}
}
public class ApplicationUserManager : UserManager<ApplicationUser>
{
public ApplicationUserManager(ApplicationUserStore userStore, IOptions<IdentityOptions> optionsAccessor,
IPasswordHasher<ApplicationUser> passwordHasher,
IEnumerable<IUserValidator<ApplicationUser>> userValidators,
IEnumerable<IPasswordValidator<ApplicationUser>> passwordValidators, ILookupNormalizer keyNormalizer,
IdentityErrorDescriber errors, IServiceProvider services, ILogger<ApplicationUserManager> logger) :
base(userStore, optionsAccessor, passwordHasher, userValidators, passwordValidators, keyNormalizer, errors,
services, logger)
{
}
}
public class ApplicationRoleStore : RoleStore<ApplicationRole, MyIndentityContext>
{
public ApplicationRoleStore(MyIndentityContext dbContext, IdentityErrorDescriber identityErrorDescriber)
: base(dbContext, identityErrorDescriber)
{}
}
public class ApplicationUserStore : UserStore<ApplicationUser, ApplicationRole, MyIndentityContext, string>
{
public ApplicationUserStore(MyIndentityContext dbContext, IdentityErrorDescriber identityErrorDescriber)
: base(dbContext, identityErrorDescriber)
{}
}
public class ApplicationUser : IdentityUser {}
public class ApplicationRole : IdentityRole
{
public ApplicationRole() { }
public ApplicationRole(string roleName) : base(roleName) { }
public ApplicationRole(string roleName, string roleDescription) : base(roleName)
{
Description = roleDescription;
}
}
[Authorize]
[ApiController]
[Route("api/[controller]")]
[EnableCors(CORS.AllowSpecificOrigins)]
public class UserController : BaseController
{
private readonly ApplicationUserManager _applicationUserManager;
public UserController(ApplicationUserManager applicationUserManager)
{
_applicationUserManager = applicationUserManager;
}
// GET: api/User/5
[HttpGet("{id}")]
public async Task<UserDTO> Get(int id)
{
var currentuser = await _applicationUserManager.FindByNameAsync("NAME");
return ...;
}
}
编辑:
在按照用户“Camilo Terevinto”的建议进行操作后,我成功了,但我还必须更改所有管理器的构造函数。例如,我必须通过IRoleStore roleStore更改ApplicationRoleStore roleStore
解决方案
使用依赖注入时,具有依赖关系的类不要求实现,它们要求契约。
这:
private readonly ApplicationUserManager _applicationUserManager;
public UserController(ApplicationUserManager applicationUserManager)
{
_applicationUserManager = applicationUserManager;
}
应该:
private readonly UserManager<ApplicationUser> _applicationUserManager;
public UserController(UserManager<ApplicationUser> applicationUserManager)
{
_applicationUserManager = applicationUserManager;
}
另外,请注意您不需要任何这些行,这些行已经由之前的调用.AddIdentity
及其选项添加。
servicesCollection.AddTransient<UserManager<ApplicationUser>, ApplicationUserManager>();
servicesCollection.AddTransient<SignInManager<ApplicationUser>, ApplicationSignInManager>();
servicesCollection.AddTransient<RoleManager<ApplicationRole>, ApplicationRoleManager>();
servicesCollection.AddTransient<IUserStore<ApplicationUser>, ApplicationUserStore>();
servicesCollection.AddTransient<IRoleStore<ApplicationRole>, ApplicationRoleStore>();
推荐阅读
- java - 用户可以重载java中类的默认构造函数这是对还是错?
- java - 带有 Recyclerview 的 Exoplayer
- bokeh - 散景:如何将网格导出为给定大小的 png?
- bash - 如何在 Linux 上替换所有包含特定文本的文件中的文本?
- sql-server - 在 Google Cloud VM SQL Server 上查找备份
- javascript - 如何操作 jQuery 克隆来删除属性
- javascript - 将函数值传递给表单中的隐藏字段
- formatting - 在没有 -style=file 选项的情况下调用 clang-format 的默认行为是什么?
- javascript - rails6 / 接收来自 vanilla js 请求的 js.erb 响应
- json - boto3 如何将 dict / json 输出上传到 s3 存储桶?