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 typeIUserStore<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 typeSystem.Data.Common.DbConnectionis an abstract class and cannot be constructed. Do you miss type mapping?
Here is some information from the stack trace:
InvalidOperationExceptionAn 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.
ResolutionFailedExceptionDependency 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 typeTToin the generic type or method below:UnityContainerExtensions.RegisterType<TFrom, TTo> (IUnityContainer, params InjectionMember[])There is no implicit conversion of links from
RoleStore<IdentityRole>toIRoleStore<IdentityRole>.
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()); 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());