The current types, IUserStore <ApplicationUser> and DbConnection, are an interface and an abstract class, respectively, and cannot be built

If I search before http://localhost:58472/Account/Register , I have this exception

System.InvalidOperationException: current type IUserStore<ApplicationUser> is an interface and cannot be constructed. Do you miss type mapping?

Here is my code:

 public class ApplicationUserManager : UserManager<ApplicationUser> { public ApplicationUserManager(IUserStore<ApplicationUser> store) : base(store) { } public static ApplicationUserManager Create( IdentityFactoryOptions<ApplicationUserManager> options, IOwinContext context) { var manager = new ApplicationUserManager( new UserStore<ApplicationUser>(context.Get<ApplicationDbContext>()) ); // other code return manager; } } 

and here is the code in the controller:

 [Authorize] public class AccountController : Controller { private ApplicationSignInManager _signInManager; private ApplicationUserManager _userManager; public AccountController() { } public AccountController( ApplicationUserManager userManager, ApplicationSignInManager signInManager) { UserManager = userManager; SignInManager = signInManager; } public ApplicationSignInManager SignInManager { get { return _signInManager ?? HttpContext.GetOwinContext().Get<ApplicationSignInManager>(); } private set { _signInManager = value; } } public ApplicationUserManager UserManager { get { return _userManager ?? HttpContext.GetOwinContext().GetUserManager<ApplicationUserManager>(); } private set { _userManager = value; } } [HttpGet] [AllowAnonymous] public ActionResult Login(string returnUrl) { ViewBag.ReturnUrl = returnUrl; return View(); } } 

So, you can see if you are reading my code, I did not change anything in the source code when creating a new MVC project, but I have the error above. What am I wrong?

I well created a new controller called ProfileController with the same code as in my second code block, but without ApplicationSignInManager , because I do not need it.

I also use the Unity container to register and manage services. Here is the code:

 public static class UnityConfig { public static void RegisterComponents() { var container = new UnityContainer(); container.RegisterType<IGenericRepo<Category>, GenericRepo<Category>>(); container.RegisterType<ICategoryService, CategoryService>(); //container.RegisterType<IUser, ApplicationUser>(); DependencyResolver.SetResolver(new UnityDependencyResolver(container)); } } 

If I uncomment the line in the code above, there is no difference when starting the site.


Update:

Commenting on @Jay, I added this code to the Unity manager.

 container.RegisterType<IUserStore<ApplicationUser>, UserStore<ApplicationUser>>(); 

Now I have this exception:

System.InvalidOperationException : The current type System.Data.Common.DbConnection is an abstract class and cannot be constructed. Do you miss type mapping?

Here is some information from the stack trace:

  • InvalidOperationException

    An error occurred while trying to create a controller of type AccountController . Make sure that the controller does not have a constructor without parameters.

    Yes, I have a public constructor without a pair.

  • ResolutionFailedException

    Dependency resolution failed, type = "AccountController" , name = "(none)" .

So, I added this line to the Unity manager:

 container.RegisterType<IDbConnection, DbConnection>(); 

But I still have the same exception.

The current type, System.Data.Common.DbConnection ...


Update:

Commenting on @RandyLevy, I tried this, helping with this question Configure Unity DI for Identity ASP.NET :

  • Adding this to AccountController :

     // two fields added private readonly UserManager<ApplicationUser> _userManager; private readonly RoleManager<IdentityRole> _roleManager; // constructor added public AccountController( IUserStore<ApplicationUser> userStore, IRoleStore<IdentityRole> roleStore, ApplicationSignInManager signInManager) { _userManager = new UserManager<ApplicationUser>(userStore); _roleManager = new RoleManager<IdentityRole>(roleStore); SignInManager = signInManager; // I need this } public ApplicationSignInManager SignInManager // I need this { get { return _signInManager ?? HttpContext.GetOwinContext().Get<ApplicationSignInManager>(); } private set { _signInManager = value; } } public UserManager<ApplicationUser> UserManager // replace by other property // type of ApplicationUserManager { get { return _userManager ?? HttpContext.GetOwinContext().GetUserManager<ApplicationUserManager>(); } //private set // comment this because _usermanager is readonly. //{ // _userManager = value; //} } //public ApplicationUserManager UserManager // replaced by the property type of // // UserManager<ApplicationUser> //{ // get // { // return _userManager ?? // HttpContext.GetOwinContext().GetUserManager<ApplicationUserManager>(); // } // private set // { // _userManager = value; // } //} 
  • Adding this to UnityManager:

     InjectionConstructor accountInjectionConstructor = new InjectionConstructor(new ApplicationDbContext()); container.RegisterType<AccountController>(); container.RegisterType<IController, Controller>(); container.RegisterType <IRoleStore<IdentityRole>, RoleStore<IdentityRole>> (accountInjectionConstructor); // on this line container.RegisterType <IUserStore<ApplicationUser>, UserStore<ApplicationUser>> (accountInjectionConstructor); 

But I have this error (runtime exception) in the comment line:

The type RoleStore<IdentityRole> cannot be used as a parameter of type TTo in the generic type or method below:

 UnityContainerExtensions.RegisterType<TFrom, TTo> (IUnityContainer, params InjectionMember[]) 

There is no implicit conversion of links from RoleStore<IdentityRole> to IRoleStore<IdentityRole> .

+5
source share
2 answers

Finally, I found a solution to my problem. I will add this code to the Unity manager.

 container.RegisterType<DbContext, ApplicationDbContext>(new HierarchicalLifetimeManager()); container.RegisterType<UserManager<ApplicationUser>>(new HierarchicalLifetimeManager()); container.RegisterType<IUserStore<ApplicationUser>, UserStore<ApplicationUser>>(new HierarchicalLifetimeManager()); container.RegisterType<AccountController>(new InjectionConstructor()); 
+13
source

Update for H. Pauwelyn. The original problem for this is that Unity is trying to invoke a constructor with two parameters.

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

In the next line, Unity will invoke the constructor without parameters, and nothing else will be needed. It worked for me.

 container.RegisterType<AccountController>(new InjectionConstructor()); 
+2
source

Source: https://habr.com/ru/post/1243235/


All Articles