【问题标题】:ASP.NET Core Access User.Identity in Controller ConstructorASP.NET Core 访问控制器构造函数中的 User.Identity
【发布时间】:2018-06-27 19:59:45
【问题描述】:

我有一个场景,我需要在构造函数的控制器中访问 User.Identity 声明。

我需要这个,因为声明包含我启动自定义数据库上下文(连接字符串)所需的信息

我该如何访问它?我只是注入 DBContext,但根据用户,他们可能需要访问不同的数据库。

有没有更好的方法来思考这个问题?

[Authorize]
public class DefaultController : Controller
{
    public DefaultController()
    {
        // this is NULL
        var authenticatedUser = User.Identity.Name;
    }
}

【问题讨论】:

  • 向我们展示需要它的类的示例代码。
  • 我只需要在控制器构造函数中访问 User.Identity。
  • 您应该向我们展示您尝试过的内容,然后我们修改那里的示例以帮助您了解如何访问您正在寻找的数据。
  • 在控制器构造函数中访问User 将始终为空。您对此无能为力。尝试使用ActionFilter

标签: c# asp.net-core asp.net-core-mvc entity-framework-core


【解决方案1】:

从 ASP.NET Core 2.1 版开始,提供了HttpContextAccessor。为此,我们必须遵循以下步骤:

使用Startup.csConfigureServices方法中的标准实现配置服务:

services.AddHttpContextAccessor();

在控制器上执行IHttpContextAccessor 的依赖注入。使用HttpContext 属性访问User

[Authorize]
public class DefaultController : Controller
{
    public DefaultController(IHttpContextAccessor contextAccessor)
    {
        // Here HttpContext is not Null :)
        var authenticatedUser = contextAccessor.HttpContext.User.Identity.Name;
    }
}

【讨论】:

  • 正确但用户仍为空。
  • 你必须检查你是否在启动时有正确的配置,这对我有用
  • 我这样做了,但是我的 IIS 配置不正确,这样做修复了它。您可以打开 IIS 并: 1-激活 Windows 身份验证; 2-禁用匿名身份验证。来自here
【解决方案2】:

要在 .Net 核心中访问 User.Identity 声明,您需要使用 HttpContext。这是我的以下实现

第一次注册

services.AddSingleton<IActionContextAccessor, ActionContextAccessor>();

然后在Service或Controller类中注册

private readonly IHttpContextAccessor _httpContextAccessor;

public UserService(
            IHttpContextAccessor httpContextAccessor,
            IUnitOfWork unitOfWork,
            UserManager<User> userManager,
            SignInManager<User> signInManager,
            RoleManager<ApplicationRole> roleManager)
        {
            _httpContextAccessor = httpContextAccessor;
            _unitOfWork = unitOfWork;
            _userManager = userManager;
            _signInManager = signInManager;
            _roleManager = roleManager;
            _currentUserGuid = _httpContextAccessor?.HttpContext?.User?.FindFirst(UserClaimsKey.Sub)?.Value;
            _currentUserName = _httpContextAccessor?.HttpContext?.User?.Identity?.Name;
            _currentUserEmail = _currentUserGuid == null ? "" : userManager.FindByIdAsync(_currentUserGuid)?.Result?.Email;
        }

实现细节可以看here

如果您有任何问题,请告诉我

【讨论】:

    【解决方案3】:
     This code I using to get the calims
    
     --------
    
          int user_id = 0;
          int Account_id = 0;
          List<string> roles;
    
        public TEMP_CON_Controller(DatabaseContext context,IHttpContextAccessor,httpContextAccessor)
        {
          _context = context;
          if (httpContextAccessor.HttpContext.User.Identity.IsAuthenticated)
          {
            var user = httpContextAccessor.HttpContext.User;
    
            this.user_id = int.Parse(user.Claims.FirstOrDefault(c => c.Type == ClaimTypes.NameIdentifier)?.Value);
    
            IEnumerable<Claim> claims = user.Claims;
    
            var accId = claims.Where(x => x.Type == "AccountId").Select(c => c.Value).SingleOrDefault();
    
            if (!string.IsNullOrEmpty(accId))
              this.Account_id = Int32.Parse(accId);
    
            roles = claims.Where(x => x.Type == ClaimTypes.Role).Select(c => c.Value).ToList();
    
    
          }
        }
    ​
    

    【讨论】:

    • 我看到 httpContextAccessor.HttpContext.User 为 NULL
    • 可能是你的startup.cs配置没有完成看这个链接检测配置:dotnetcoretutorials.com/2017/01/05/…
    • 你说你可以在你的控制器构造函数中访问用户?似乎与其他人所说的相矛盾
    • 控制器或任何 C# 文件中的任何内容......您应该在 if 语句中编写代码以获取用户信息,此代码我在项目中使用
    【解决方案4】:

    来自以上链接的 Rabea AlTaradeh:

        Startup.cs
         //services section
         services.AddSingleton<IHttpContextAccessor, HttpContextAccessor>();
    
    [Authorize]
    public class HomeController : Controller
    {
      #region DI         
      private string UserEmail;
      private readonly IHttpContextAccessor _httpContextAccessor;
      public HomeController(IHttpContextAccessor httpContextAccessor)
      {
        _httpContextAccessor = httpContextAccessor;
        UserEmail = _httpContextAccessor.HttpContext.User.Claims
                    .FirstOrDefault(c => c.Type == "preferred_username")?.Value;
    
      }
      #endregion DI 
       public IActionResult Index()
       {            
          ViewBag.UserEmail = UserEmail;   
          return View();
       }
    }
    

    【讨论】:

    • 我使用的是 asp net core 2.2
    【解决方案5】:

    在 Asp.net Core v.2+ 中,您不必注入 HttpContext 或其他东西。像这样访问用户:

    public IActionResult GetMe()
    {
        return Ok(User.Identity.Name);
    }
    

    【讨论】:

    • 这将在控制器方法中工作,因为已经定义了用户。问题是关于访问构造函数中的 User 成员,除非您使用 HttpContextAccessor,否则该成员不可用,如 batressc 的帖子所示。
    猜你喜欢
    • 2018-05-25
    • 2010-11-03
    • 1970-01-01
    • 2020-09-01
    • 1970-01-01
    • 1970-01-01
    • 2017-05-25
    • 1970-01-01
    • 2011-05-27
    相关资源
    最近更新 更多