1

I have already searched similar questions, but since some of the Syntax has changed, I haven't found the answer I am looking for yet.

I am trying to pass a UserID from the Login/HomeController, so alle Controller/Views of the application can access it. The Login is hard coded at the moment, as I am simply trying to pass a value right now.

Session["key"] does not work and neither does HttpContext.Current, which doesn't even exist in the newest MVC version. In the HomeController itself I can add values with HttpContext.Session.SetString(Key, "string") but I do not know how to access it in the other controllers/views.

I have found IHttpContextAccessor, but since I have to pass this as a parameter in every single constructor in all the class I want to use it and I already pass a cache parameter, it seems rather 'overkill'

Is there no better way to pass a UserID to all controller?

This is my startup.cs

        public void ConfigureServices(IServiceCollection services)
        {
            services.AddControllersWithViews();
            services.AddSingleton<ILocationContainer, LocationContainer>();
            services.AddDistributedMemoryCache();
            services.AddHttpContextAccessor();
            services.AddSession(options => {
                options.IdleTimeout = TimeSpan.FromMinutes(20);
                options.Cookie.HttpOnly = true;
                options.Cookie.IsEssential = true;
            });
            services.AddMvc();

        }


        public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
        {


            app.UseAuthorization();

            app.UseSession();
            app.UseEndpoints(endpoints =>
            {
                endpoints.MapControllerRoute(
                    name: "default",
                    pattern: "{controller=Home}/{action=Index}/{id?}");
            });
        }

This is my code in the Controller

public IActionResult Login()
        {
            HttpContext.Session.SetString(UserAccount, "blabla");
            HttpContext.Session.SetString(UserRole, "admin");
            return RedirectToAction("Index", "Home");

        }
Link
  • 61
  • 1
  • 7
  • This is precisely the kind of data you do not need to pass around. If you are using identity just use the mechanisms available to get this data when you need it. – Jonathan Alfaro Jun 19 '20 at 20:58

2 Answers2

0

Until ASP.NET Core 1.0 RC1 : It's User.GetUserId() from System.Security.Claims namespace.

Since ASP.NET Core 1.0 RC2 : You now have to use UserManager

in the Controller you need something like this:

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

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

public async Task<IActionResult> YourMethodName()
 {
    var userId =  User.FindFirstValue(ClaimTypes.NameIdentifier) // will give the user's userId
    var userName =  User.FindFirstValue(ClaimTypes.Name) // will give the user's userName

    ApplicationUser applicationUser = await _userManager.GetUserAsync(User);
    string userEmail = applicationUser?.Email; // will give the user's Email
 }
}

It's a lot of info in this aspect you have to read this: https://stackoverflow.com/a/52135130

CristiC777
  • 481
  • 11
  • 20
  • 1
    Thank you for your help, I have solved it now with IHttpContextAccessor, as we can not really Identity classes, see comment above – Link Jun 20 '20 at 08:28
0

You can create a base controller and inherit in every controller that you need User Info .

  public class CustomBaseController : ControllerBase
  {
            public UserInfo UserInfo
            {
                Id = User.FindFirstValue(ClaimTypes.NameIdentifier),
                Name = User.FindFirstValue(ClaimTypes.Name),
                PhoneNumber = User.FindFirstValue("PhoneNumber")    
            };
  }

public class UserController : CustomBaseController
{
    public IActionResult Login()
    {
        var user = _context.User.Find(UserInfo.Id);

        // some code
    }
}
  • Thank you for your help, unfortunately we are not supposed to use EF Frameworks or even any kind of database (we use JSON export/import, don't ask me why, college...) and so working with Identity would be quite complicated. I have solved it now by using IHttpContextAccessor, although Identity would make coding a lot easier, especially when it comes to UserRoles... – Link Jun 20 '20 at 08:27