如何在 initialize() 方法中使用 userManager ASP.net MVC 5

How to use userManager in initialize() method ASP.net MVC 5

(对于 TL;DR 版本请跳过此部分)

我试图让用户使用他的个人资料中的选项来设置我网站的首选语言。我在 99% 时全部工作:当用户更新他的个人资料并设置 cookie "language" 时,AccountController 保存文化。然后,该网站将完美地更改其显示语言。但是,我仍然需要在用户第一次登录时设置网站语言,而无需更新他的个人资料来创建 cookie。

因此,我试图通过覆盖基本控制器的 Initialize() 函数在应用程序周期的早期设置 cookie。问题是我无法访问用户首选项,因为 UserManager 为空。有没有办法从 baseController 的 initialize() 函数访问保存在数据库中的用户语言偏好?

TL;DR version: baseController 的 initialize() 函数中的 userManager 为 null。如何从那里访问当前用户变量?

     protected override void Initialize(RequestContext requestContext)
    {
        try
        {
            String culture = requestContext.HttpContext.GetOwinContext().Request.Cookies["language"];
            if(culture != null)
            {
                Thread.CurrentThread.CurrentCulture = CultureInfo.GetCultureInfo(culture);
                Thread.CurrentThread.CurrentUICulture = CultureInfo.GetCultureInfo(culture);
            }
            else
            {
                if (requestContext.HttpContext.User.Identity.IsAuthenticated)
                {
                    String userName = requestContext.HttpContext.User.Identity.GetUserName();
                    ApplicationUser user = UserManager.FindByName(userName); //TODO: UserManager is NULLL !!!

                    HttpCookie language = new HttpCookie("language");
                    if (user.DefaultLanguage)
                    {
                        language.Value = "fr-CA";
                    }
                    else
                    {
                        language.Value = "en-CA";
                    }
                    Response.Cookies.Add(language);
                }

            }
        }
        catch (Exception e)
        {

        }
        base.Initialize(requestContext);

    }

我刚刚又看了一遍问题。我对答案做了一些小改动。

您根本不应该为此使用 UserManager。只需使用该语言向 ClaimsIdentity 添加声明即可。这也防止了对数据库的额外调用。

将语言 属性 添加到 AppicationUser。确保将其添加为声明:

public class ApplicationUser : IdentityUser
{
    public string Language { get; set; }

    public async Task<ClaimsIdentity> GenerateUserIdentityAsync(UserManager<ApplicationUser> manager)
    {
        var userIdentity = await manager.CreateIdentityAsync(this, DefaultAuthenticationTypes.ApplicationCookie);

        // Add custom user claims here
        userIdentity.AddClaim(new Claim("Language", Language));

        return userIdentity;
    }
}

在 Initialize 中,您可以这样阅读声明:

 protected override void Initialize(RequestContext requestContext)
{
    try
    {
        // Try claims collection first
        var culture = (System.Security.Claims.ClaimsIdentity)User.Identity).FindFirst("Language").Value;

        // otherwise try cookie
        if (culture == null)
            culture = requestContext.HttpContext.GetOwinContext().Request.Cookies["language"];

        if (culture == null)
        {
            // user is not logged in and there is no cookie
            culture = "fr-CA";
            HttpCookie language = new HttpCookie("language");
            language.Value = culture;
            Response.Cookies.Add(language);
        }
        Thread.CurrentThread.CurrentCulture = CultureInfo.GetCultureInfo(culture);
        Thread.CurrentThread.CurrentUICulture = CultureInfo.GetCultureInfo(culture);
    }
    catch (Exception e)
    {
    }
    base.Initialize(requestContext);
}

像这样。仍然没有测试它,但这是这个想法。 如果有不清楚的地方请告诉我。