2

In the DB i have Role and User entities with one to many relationship.

What i am trying to do is to build custom authorization filter. All the tutorials that i have seen are using default ASP.NET membership. All i know is that i need to inherit AuthorizationAttribute but do not know which methods do i need to override and how to implement them.

public class UserAuth : AuthorizeAttribute
{

}

In the DB:

Role

public class Role
{
    [Key]
    public int RoleID { get; set; }

    [Required]
    public int RolenameValue { get; set; }

    [MaxLength(100)]
    public string Description { get; set; }

    // // // // //

    public Rolename Rolename 
    {
        get { return (ProjectName.Domain.Enums.Rolename)RolenameValue; }
        set { RolenameValue = (int)value; }
    }

    public virtual ICollection<User> Users { get; set; }
}

User

public class User
{
    [Key]
    public int UserID { get; set; }

    [Required]
    [MaxLength(30)]
    public string Username { get; set; }

    [Required]
    [MinLength(5)]
    public string Password { get; set; }

    [Required]
    [DataType(DataType.EmailAddress)]
    public string Email { get; set; }

    [MaxLength(30)]
    public string FirstName { get; set; }

    [MaxLength(50)]
    public string LastName { get; set; }

    [DataType(DataType.Date)]
    public DateTime Birthdate { get; set; }

    public int GenderValue { get; set; }

    // // // // // // //

    public Gender Gender
    {
        get { return (ProjectName.Domain.Enums.Gender)GenderValue; }
        set { GenderValue = (int)value; }
    }

    public int RoleID { get; set; }

    [ForeignKey("RoleID")]
    public Role Role { get; set; }

1 Answer 1

7

You don't need to create a custom attribute. You can use existing AuthoriseAttribute but what you should do is implement custom Principal class that will use your own roles from DB. In your Principal class you will implement IsInRole method:

public bool IsInRole(string role)
{
    if(this.Roles == null)
        this.Roles = DependencyResolver.Current
           .GetService<ISecurityService>()
           .GetUserPermissions(this.Identity.Name);

    return this.Roles.Any(p => p.Name == role);
}

You should set your custom Principal in Global.asax

    void OnPostAuthenticateRequest(object sender, EventArgs e)
    {
         // Get a reference to the current User 
        IPrincipal user = HttpContext.Current.User; 

        // If we are dealing with an authenticated forms authentication request         
        if (user.Identity.IsAuthenticated && user.Identity.AuthenticationType == "Forms") 
        { 
            // Create custom Principal 
            var principal = new MyCustomPrincipal(user.Identity); 

            // Attach the Principal to HttpContext.User and Thread.CurrentPrincipal 
            HttpContext.Current.User = principal; 
            System.Threading.Thread.CurrentPrincipal = principal; 
        }
    } 
Sign up to request clarification or add additional context in comments.

3 Comments

+1, I do it in the same way, except that I load all roles through my Authorization repository in OnPostAtuthenticate.
How to implement MyCustomPrincipal? :P EDIT: I mean, how to properly implement it. Only with IsInRole() ?
Derive from GenericPrincipal (msdn.microsoft.com/en-us/library/…) or implement IPrincipal interface

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.