可以将文章内容翻译成中文,广告屏蔽插件可能会导致该功能失效(如失效,请关闭广告屏蔽插件后再试):
问题:
I'm using Unity successfully for all regular constructor injection such as repositories etc., but I can't get it working with the ASP.NET Identity classes. The setup is this:
public class AccountController : ApiController { private UserManager _userManager { get; set; } public AccountController(UserManager userManager) { if (userManager == null) { throw new ArgumentNullException("userManager"); } _userManager = userManager; } // ... }
with these configs for Unity:
unity.RegisterType(); unity.RegisterType>(new HierarchicalLifetimeManager()); unity.RegisterType, UserStore>(new HierarchicalLifetimeManager());
That's the same as other posts here for Autofac, Ninject e.g., but it doesn't work in my case. The error message is:
An error occurred when trying to create a controller of type 'AccountController'. Make sure that the controller has a parameterless public constructor. Manual creation works of course:
public AccountController() : this(new UserManager(new UserStore("Mongo"))) { }
What's wrong?
UPDATE
As suggested by @emodendroket, shortening the code to this does the trick. No need for the Unity.Mvc package.
unity.RegisterType, MyCustomUserStore>(new HierarchicalLifetimeManager());
and
public AccountController(UserManager _userManager, IAccountRepository _account) { // ...
回答1:
You also need to resolve the UserManager. The following is an example how you could do it with the UserManager and the RoleManager. In this sample I use the regular Unity 3 package instead of one of the derivates or bootstrappers (had some problems with them in the past).
AccountController
private readonly UserManager _userManager; private readonly RoleManager _roleManager; public AccountController(IUserStore userStore, IRoleStore roleStore) { _userManager = new UserManager(userStore); _roleManager = new RoleManager(roleStore); }
Unity Bootstrapper
var accountInjectionConstructor = new InjectionConstructor(new IdentitySampleDbModelContext(configurationStore)); container.RegisterType, UserStore>(accountInjectionConstructor); container.RegisterType, RoleStore>(accountInjectionConstructor);
回答2:
As this blog post from enterpriseframework.com says:
First, add the Unity Bootstrapper for ASP.NET MVC Nuget package.
In your Visual Studio "Solution Explorer" > right click on your Web project's "References" node > click "Manage NuGet Packages".
From the left menu, choose Online > All
- In the upper right search box > Search Online (Ctrl + E) > type "Unity bootstrapper for ASP.NET MVC".
- Select "Unity Bootstrapper for ASP.NET MVC" and choose Install.
- Click Close after install completes
Then Modify your-Web-project/App_Start/UnityConfig.cs
file and update the using
statements as follows:
using System; using System.Data.Entity; using Microsoft.AspNet.Identity; using Microsoft.AspNet.Identity.EntityFramework; using Microsoft.Practices.Unity; using Microsoft.Practices.Unity.Configuration; using MicrosoftIdentity.Controllers; using MicrosoftIdentity.Models;
Finally, in the same file, update RegisterTypes
method as below:
public static void RegisterTypes(IUnityContainer container) { // NOTE: To load from web.config uncomment the line below. Make sure to add a Microsoft.Practices.Unity.Configuration to the using statements. // container.LoadConfiguration(); // TODO: Register your types here container.RegisterType, UserStore>(); container.RegisterType>(); container.RegisterType(); container.RegisterType(); container.RegisterType(new InjectionConstructor()); }
HTH
回答3:
Install-Package Unity.AspNet.WebApi
You need to register Unity under the HttpConfiguration.DependencyResolver
property. This allows WebApi
to know that it needs to use Unity rather than reflection to instanciate your controllers.
The easiest way to do this is with the above nuget package.
回答4:
Replace this property in the AccountController
public ApplicationUserManager UserManager { get { _userManager = new ApplicationUserManager( new UserStore(new ApplicationDbContext())); return _userManager ?? Request.GetOwinContext().GetUserManager(); } private set { _userManager = value; } }