访问AccountController外部的UserManager

时间:2015-03-27 03:01:47

标签: asp.net-mvc asp.net-mvc-5 asp.net-identity-2 actioncontroller

我正在尝试从不同的控制器(不是aspnetuser)设置accountcontroller表中列的值。我一直在尝试访问UserManager,但我无法确定如何操作。

到目前为止,我已经在控制器中尝试了以下内容:

    ApplicationUser u = UserManager.FindById(User.Identity.GetUserId());
    u.IsRegComplete = true;
    UserManager.Update(u);

这不会编译(我认为因为UserManager尚未实例化控制器)

我还尝试在AccountController中创建一个公共方法来接受我想要更改值的值并在那里执行,但我无法弄清楚如何调用它。

public void setIsRegComplete(Boolean setValue)
{
    ApplicationUser u = UserManager.FindById(User.Identity.GetUserId());
    u.IsRegComplete = setValue;
    UserManager.Update(u);

    return;
}

如何在帐户控制器之外访问和编辑用户数据?

更新:

我尝试在其他控制器中实例化UserManager,如下所示:

    var userManager = new UserManager<ApplicationUser>(new UserStore<ApplicationUser>(db));
    ApplicationUser u = userManager.FindById(User.Identity.GetUserId());

我的项目符合(有点兴奋)但是当我运行代码时出现以下错误:

Additional information: The entity type ApplicationUser is not part of the model for the current context.

更新2:

我已将该功能移至IdentityModel(不要问我在这里抓着吸管),如下所示:

   public class ApplicationUser : IdentityUser
    {
        public async Task<ClaimsIdentity> GenerateUserIdentityAsync(UserManager<ApplicationUser> manager)
        {
            // Note the authenticationType must match the one defined in CookieAuthenticationOptions.AuthenticationType
            var userIdentity = await manager.CreateIdentityAsync(this, DefaultAuthenticationTypes.ApplicationCookie);
            // Add custom user claims here
            return userIdentity;
        }
        public Boolean IsRegComplete { get; set; }

        public void SetIsRegComplete(string userId, Boolean valueToSet)
        {

            var userManager = new UserManager<ApplicationUser>(new UserStore<ApplicationUser>());
            ApplicationUser u = new ApplicationUser();
            u = userManager.FindById(userId);

            u.IsRegComplete = valueToSet;
            return;
        }
    }

但是我仍然得到以下内容:

The entity type ApplicationUser is not part of the model for the current context.

IdentitiesModels.cs中还有以下类:

public class ApplicationDbContext : IdentityDbContext<ApplicationUser>
{
    public ApplicationDbContext()
        : base("DefaultConnection", throwIfV1Schema: false)
    {
    }

    public static ApplicationDbContext Create()
    {
        return new ApplicationDbContext();
    }
}

我在这里做错了什么?感觉就像我正在咆哮着错误的树。我所要做的就是从不同控制器(即不是AccountsController)的操作更新aspnetuser表中的列。

5 个答案:

答案 0 :(得分:30)

如果您使用的是默认项目模板,则会按以下方式创建UserManager

在Startup.Auth.cs文件中,有一行如下:

app.CreatePerOwinContext<ApplicationUserManager>(ApplicationUserManager.Create);

使OWIN管道在每次请求到达服务器时实例化ApplicationUserManager的实例。您可以使用控制器中的以下代码从OWIN管道获取该实例:

Request.GetOwinContext().GetUserManager<ApplicationUserManager>()

如果仔细查看AccountController课程,您会看到以下可以访问ApplicationUserManager的代码:

    private ApplicationUserManager _userManager;

    public ApplicationUserManager UserManager
    {
        get
        {
            return _userManager ?? Request.GetOwinContext().GetUserManager<ApplicationUserManager>();
        }
        private set
        {
            _userManager = value;
        }
    }

请注意,如果您需要实例化ApplicationUserManager类,则需要使用ApplicationUserManager.Create静态方法,以便应用适当的设置和配置。

答案 1 :(得分:3)

如果您必须在另一个控制器中获取UserManager的实例,只需在Controller的构造函数中添加其参数,就像这样

public class MyController : Controller
{
    private readonly UserManager<ApplicationUser> _userManager;

    public MyController(UserManager<ApplicationUser> userManager)
    {
        _userManager = userManager;;
    }
}

但我必须将UserManager放在一个非控制器的类中!

任何帮助都将不胜感激。

<强>更新

我在考虑你使用的是asp.net核心

答案 2 :(得分:1)

对于MVC 5

  

在帐户控制器外部访问usermanger或createUser的步骤很简单。请按照以下步骤

  1. 创建一个控制器,考虑使用SuperAdminController
  2. 如下所示装饰与AccountController相同的SuperAdminController,

    private readonly IAdminOrganizationService _organizationService;
    private readonly ICommonService _commonService;
    private ApplicationSignInManager _signInManager;
    private ApplicationUserManager _userManager;
    
    public SuperAdminController()
    {
    }
    
    public SuperAdminController(ApplicationUserManager userManager, ApplicationSignInManager signInManager)
    {
        UserManager = userManager;
        SignInManager = signInManager;
    }
    
    public SuperAdminController(IAdminOrganizationService organizationService, ICommonService commonService)
    {
        if (organizationService == null)
            throw new ArgumentNullException("organizationService");
    
    
        if (commonService == null)
            throw new ArgumentNullException("commonService");
    
        _organizationService = organizationService;
        _commonService = commonService;
    }
    
    
    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;
        }
    }
    
  3. 在操作中创建用户方法

    [HttpPost]
    public async Task<ActionResult> AddNewOrganizationAdminUser(UserViewModel userViewModel)
    {
        if (!ModelState.IsValid)
        {
            return View(userViewModel);
        }
    
        var user = new ApplicationUser { UserName = userViewModel.Email, Email = userViewModel.Email };
        var result = await UserManager.CreateAsync(user, userViewModel.Password);
        if (result.Succeeded)
        {
            var model = Mapper.Map<UserViewModel, tblUser>(userViewModel);
    
            var success = _organizationService.AddNewOrganizationAdminUser(model);
    
            return RedirectToAction("OrganizationAdminUsers", "SuperAdmin");
    
        }
        AddErrors(result);
        return View(userViewModel);
    }
    

答案 3 :(得分:0)

我遇到了同样的问题并修改了我的代码,以便将对UserManager类的引用从Controller传递给模型:

//snippet from Controller
public async Task<JsonResult> UpdateUser(ApplicationUser applicationUser)
{
    return Json(await UserIdentityDataAccess.UpdateUser(UserManager, applicationUser));
}

//snippet from Data Model
public static async Task<IdentityResult> UpdateUser(ApplicationUserManager userManager, ApplicationUser applicationUser)
{
    applicationUser.UserName = applicationUser.Email;
    var result = await userManager.UpdateAsync(applicationUser);

    return result;
}

答案 4 :(得分:0)

如果您需要在控制器之外访问 UserManager,您可以使用以下方法:

var userStore = new UserStore<ApplicationUser>(new ApplicationDbContext());
var applicationManager = new ApplicationUserManager(userStore);