0
votes

We have an Intranet site we are developing in ASP.NET 5 aka vNext and MVC 6.

We'd like to be able to get the Windows Network ID the user is logged in as, but then there is an existing database defining roles, etc. we were going to leverage and have already done so. Really all I want to do is get the Windows user ID while using ASP.NET Identity to manage roles the user has access to. Any suggestions how to accomplish this?

Essentially in Startup.cs I have something like below in Configure Services:

    services.AddIdentity<WorldUser, IdentityRole>(config =>
    {
       config.User.RequireUniqueEmail = true;
       config.Password.RequiredLength = 8;
    }).AddEntityFrameworkStores<WorldContext>();

Next in Configure I have: app.UseIdentity();

Windows Authentication is on at the project properties level and so is Anonymous. I see no way to actually get the Windows User ID.

2
I am going to delete my answer, since it does not work. But I do not want it to look like I am shirking my commitment, so... As soon as the 48 hours SO initial wait is over, and I am allowed to start a bounty, I will start a bounty and award 100 rep points to the first person to have answered this correctly, whether the answer comes before or after the bounty.user4843530
Brian, have you looked at this stackoverflow.com/a/10584919/4843530. Let me know if it helps, as I will want to try to work it out. Seems like we have a very similar need and problem.user4843530
Sorry I missed this earlier. It was a good thought but running the code under IIS Express, that code "var username = Thread.CurrentPrincipal.Identity.Name;" just returns an empty string for User Name. There may be a way to go into the IIS Express config file to make it return the Windows ID. Will try that too.Brian Edwards

2 Answers

0
votes

Warning: this is code for ASP.NET 4.5 not 5.

Put this is your web.config:

<system.web>
    <compilation debug="true" targetFramework="4.5" />
    <httpRuntime targetFramework="4.5" maxRequestLength="20480" />
    <authentication mode="Windows" />
    <authorization>
        <deny users="?" />                  <!--Denies access to the anonymous user.-->
        <allow users="MydomainName\MyUsername" />      <!--Grants access to this user.-->
        <allow roles="MyWindowsGroup" />
        <deny users="*" />                  <!--Denies access to everyone. This shakes out as everyone except the defined users/usergroupt that are rganted access manualy.-->
    </authorization>
</system.web>

This way you must have an Windows Network User Id. Which a user always has in an intranet application. Then just use:

HttpContext.Current.User.Identity.Name

Just as before. Like this:

String name = User.Identity.Name;
// If needed filter out the domain name here
int accessLevel = _UserRepository.GetAccessLevel(name) 
// Assuming  you use a repository to connect to your database. And also have a method to get the accesslevel for a username
Session["AccessLevel"] = accessLevel;
// In case you want to check for accesslevel in the views as well you can put it in a session like so.

Once again this is code for a .NEET 4.5 and NOT a .NET 5 Application. The C# code should be identical but there is no web.config in .NET 5 so you have to put your config in via Startup.cs.

From what you are asking this seems like what you need, if any further explanation is required let me know.

0
votes

So I am still hoping someone comes up with a better answer because my goal is still to use and leverage .Net Identity for authorization after authenticating the user with their Windows User ID. But for now, I am going to enable Windows Authentication and use the solution for customizing Authorization options provided by Rick in this thread: How do you create a custom AuthorizeAttribute in ASP.NET Core?

So I will be doing the following, for each role creating a class as follows:

    public class ETimeAdmin : AuthorizationHandler<ETimeAdmin>, IAuthorizationRequirement
    {
       protected override void Handle(AuthorizationContext context, ETimeAdmin requirement)
       {



       }
    }

Then in Startup.cs in configure services I will add:

    services.AddAuthorization(options => options.AddPolicy("ETimeAdmin", policy => policy.Requirements.Add(new ETimeAdmin())));

Finally I should be able to use:

    [Authorize(Roles="ETimeAdmin")]

Instead of doing the above, what I'd like to do in Startup.cs is add this line:

     services.AddIdentity<ETimeUser, IdentityRole>(config =>
     {
     }).AddEntityFrameworkStores<ETimeContext>();

Then I could just use what is already provided with .Net Identity without writing my own code for each role. I'd have to employ my own caching so I wouldn't need to go back to the database each time I wanted to check if the user had permissions. There has to be a better way...