1

I was recently given a task to create separate login for users, that belong to certain role. Login was already implemented for main users and this was done with using Principal that was assigned to Thread.CurrentPrincipal and is later checked for value every time a page is loaded. I modified my code to use same mechanism of authentication so in my custom login I create custom Principal and assign it to Thread.CurrentPrincipal. Now the problem with that is that with custom login I override my normal login and vice versa. Is it possible to assign my principle somewhere else than Thread.CurrentPrincipal to allow for both login variants to work at the same time? If this is not possible I would like to learn about alternatives :)

Denis Vitez
  • 490
  • 7
  • 25
  • What do you mean by "separate login"? What do you mean by "I override my normal login"? – Serg Rogovtsev Sep 29 '15 at 13:01
  • Do you mean that you want your application to allow, for example, both claims based and forms based authentication? – Dbuggy Sep 29 '15 at 13:06
  • You shouldn't be changing the thread principle at all, store your authentication information in the session object, or in a cookie. If you want it to be more secure, only store an encrypted authentication key and look up the principle for authenticated users in a database or other data store. ASP.net has built-in authentication providers you should try to use. – Ron Beyer Sep 29 '15 at 13:08
  • By "separate login" I mean that some Controllers can be accessed with first type of login, while others can be accessed with my custom type of login. Logins are done using different user credentials(password, pin, ...) and using different forms. By overriding my normal login I meant that if I login as normal user and then login via my custom login the Thread.Principle is overridden with my custom principle and so main login is no longer valid. So I can assume that existing login with Thread.Principle is bad practice and I should try to implement my authentication with session or cookie? – Denis Vitez Sep 29 '15 at 13:16
  • @RonBeyer Changing the Thread principal is a very common and valid practice, such as when using a custom security principal object. Storing authentication information in the Session or a cookie doesn't make it available to the underlying provider. It just allows a way to persist it between pages. – DVK Sep 29 '15 at 13:21
  • @DVK http://stackoverflow.com/questions/3057937/difference-between-http-context-user-and-thread-currentprincipal-and-when-to-use – Ron Beyer Sep 29 '15 at 13:24

2 Answers2

2

The answer from DVK is valid, but I have had complications in the past when using custom IPrincipals. An alternative approach is to use a single principal, represented by a ClaimsPrincipal and make use of the fact that it can store multiple identities. You can then use the default implementations of IsInRole for example.

https://msdn.microsoft.com/en-us/library/system.security.claims.claimsprincipal(v=vs.110).aspx

Mike Goodwin
  • 8,430
  • 2
  • 31
  • 49
1

This is very doable, and not terribly difficult. The best way I've found to do this is to implement a custom IPrincipal that has a property that also contains an IPrincipal. Then you can store both in the thread, and implement the IsInRole method in a manner that allows checking both principal objects for authorization purposes. Some pseudo-code...

public class MyPrincipal : IPrincipal
{
    public IPrincipal FormsPrincipal { get; private set; }

    public MyPrincipal(IPrincipal formsPrincipal)
    {
        FormsPrincipal = formsPrincipal;
    }

    public bool IsInRole(string role)
    {
        if (someCondition)
        {
            // check roles for this
        }
        else
        {
            return FormsPrincipal.IsInRole(role); // check role against the other principal
        }
    }
}

Then on PostAuthenticateRequest, use the current principal to create your new, custom principal, and assign your custom principal as the HttpContext.Current principal.

Good resource with lots of detail: ASP.NET MVC - Set custom IIdentity or IPrincipal

Community
  • 1
  • 1
DVK
  • 2,551
  • 1
  • 15
  • 20
  • 1
    I created CustomPrinciple that holds my two IPrinciple objects. I had some problems with getting it to work properly but it seems like it's working now. Thank you for your anwser @DVK. – Denis Vitez Sep 30 '15 at 11:53