gpt4 book ai didi

c# - 带有 IOC : "The current type is an interface and cannot be constructed" 的身份框架

转载 作者:太空宇宙 更新时间:2023-11-03 23:24:49 25 4
gpt4 key购买 nike

我必须将我们所有的 IdentityFramework 类和接口(interface)移动到单独的库中,这意味着新的 Common.Models.Interfaces界面库只能引用其他界面库(或.net 库)。这意味着我所有的ApplicationUser参数和变量变为 IApplicationUser .

经过几个小时的更改,我完成了所有构建,但在运行时出现以下错误:

The current type, Microsoft.AspNet.Identity.IUserStore`1[Common.Models.Interfaces.Account.IApplicationUser], is an interface and cannot be constructed. Are you missing a type mapping?

所以我的问题是:我可能缺少什么类型的映射?

我之前已经解决了dbcontext来自 http://tech.trailmax.info/2014/09/aspnet-identity-and-ioc-container-registration 的以下代码存在问题(具体使用InjectionConstructor)

container.RegisterType<IApplicationUser, ApplicationUser>();
container.RegisterType<DbContext, ApplicationDbContext>();
container.RegisterType<IdentityDbContext<ApplicationUser>, ApplicationDbContext>();
container.RegisterType<IIdentityMessageService, EmailService>();
container.RegisterType<IApplicationSignInManager, ApplicationSignInManager>();
container.RegisterType<IUserStore<ApplicationUser>, UserStore<ApplicationUser>>(new InjectionConstructor(typeof(ApplicationDbContext)));

注意:此处提到的其他错误已删除,因为它具有误导性。看起来我需要额外的映射,但不知道是什么。

应用程序用户界面和类如下(已删减),以便您发现我哪里出错了:

IApplicationUser.cs

public interface IApplicationUser : IUser, IUser<string>
{
...
}

应用程序用户.cs

public class ApplicationUser : IdentityUser, IApplicationUser
{
...
}

ApplicationDbContext.cs

public class ApplicationDbContext : IdentityDbContext<ApplicationUser>

显然不可能包含所有相关代码来重现此代码,因为它运行到 1000 行,并且不需要重现,因此只有 IOC 专家应该申请。 :)

第二次尝试:

在来自 @guillaume31 的有用链接之后我尝试了以下方法:

container.RegisterType(typeof(IUserStore<>), typeof(UserStore<>), new InjectionConstructor(typeof(ApplicationDbContext)));

编译通过了,但是我得到了一个新的错误:

GenericArguments[0], 'Common.Models.Interfaces.Account.IApplicationUser', on 'Microsoft.AspNet.Identity.EntityFramework.UserStore`6[TUser,TRole,TKey,TUserLogin,TUserRole,TUserClaim]' violates the constraint of type parameter 'TUser'

第三次尝试

container.RegisterType(typeof(IUserStore<>), typeof(UserStore<ApplicationUser>), new InjectionConstructor(typeof(ApplicationDbContext)));

导致此错误:

Unable to cast object of type 'Microsoft.AspNet.Identity.EntityFramework.UserStore1[Vero.Common.Verofy.Models.Account.ApplicationUser]' to type 'Microsoft.AspNet.Identity.IUserStore1[Vero.Common.Verofy.Models.Interfaces.Account.IApplicationUser]'.

第四次尝试

container.RegisterType(typeof(IUserStore<IApplicationUser>), typeof(UserStore<ApplicationUser>), new InjectionConstructor(typeof(ApplicationDbContext)));

这可以编译,但我得到这个错误(与之前的测试相同):

Unable to cast object of type 'Microsoft.AspNet.Identity.EntityFramework.UserStore1[Common.Models.Account.ApplicationUser]' to type 'Microsoft.AspNet.Identity.IUserStore1[Common.Models.Interfaces.Account.IApplicationUser]'.

第五次尝试(使用注册实例):

var applicationDbContext = new ApplicationDbContext();
container.RegisterInstance<DbContext>(applicationDbContext);
var userStore = new UserStore<ApplicationUser>(applicationDbContext);
container.RegisterInstance(typeof(IUserStore<IApplicationUser>), userStore);

新的错误是:

The type Microsoft.AspNet.Identity.EntityFramework.UserStore1[[Vero.Common.Verofy.Models.Account.ApplicationUser, Vero.Common.Verofy.Models, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null]] cannot be assigned to variables of type Microsoft.AspNet.Identity.IUserStore1[Vero.Common.Verofy.Models.Interfaces.Account.IApplicationUser]. Parameter name: instance

第六次尝试(旁路注入(inject)):

以下简单行在运行时也会失败:

IUserStore<IApplicationUser> test = (IUserStore<IApplicationUser>)new UserStore<ApplicationUser>(applicationDbContext);

错误是:

无法转换类型的对象 > 'Microsoft.AspNet.Identity.EntityFramework.UserStore 1[Common.Models.Account.ApplicationUser]' to type 'Microsoft.AspNet.Identity.IUserStore 1[Common.Models.Interfaces.Account.IApplicationUser]'。

总结

所有这些问题都表明我的 IUserStore<IApplicationUser> 之间不兼容。和我的 UserStore<ApplicationUser>类实现。询问您认为可能有帮助的任何类(class)的更多详细信息。

更新

基本问题归结为这种依赖性:

  • 我们的 ApplicationUser类需要暴露 public async Task<ClaimsIdentity> GenerateUserIdentityAsync(UserManager<ApplicationUser, string> manager)
  • 这会强制 UserManager属于 IApplicationUser 类型而不是应用程序用户,并导致发生大量级联依赖关系。

最佳答案

这是我用过的

        container.RegisterType<IUserStore<IdentityUser>, UserStoreRepository>(new PerRequestLifetimeManager());
container.RegisterType<IRoleStore<IdentityRole, string>, RoleStoreRepository>(new PerRequestLifetimeManager());

container.RegisterType<ApplicationUserManager>(new PerRequestLifetimeManager());
container.RegisterType<ApplicationRoleManager>(new PerRequestLifetimeManager());

UserStoreRepository 就是

public class UserStoreRepository : UserStore<IdentityUser>
{
public UserStoreRepository(AuthContext context)
: base(context)
{

}
}

同样

public class RoleStoreRepository : RoleStore<IdentityRole>
{
public RoleStoreRepository(AuthContext context)
: base(context)
{

}
}

当然你需要注册上下文

public class AuthContext: IdentityDbContext<IdentityUser>
{
public AuthContext()
: base("AuthContext")
{

}
}

对于其他事情:

public class ApplicationUserManager : UserManager<IdentityUser>

public class ApplicationRoleManager : RoleManager<IdentityRole>

我认为您的第一次尝试几乎是正确的,我会尝试将您的 UserStore 包装到另一个包装您的 ApplicationUser 的对象

关于c# - 带有 IOC : "The current type is an interface and cannot be constructed" 的身份框架,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34202416/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com