Skip to main content
5 of 8
added 14 characters in body
Engineert
  • 929
  • 1
  • 6
  • 18

I highly recommend separate your project as layers and have a Service Layer that can be used by your many projects such as MVC and/or Background Jobs and you can add this Authorization Service to Service Layer. So you can call this Authorization Service Layer.

This way, you don't need to extend Authorization to the Model layer because your other entry-points can call this layer. Besides, Models is not responsible about Authentication. It is worse than being on Controllers.

Additionally, there are kind of authorization such as Role-Right Management. These authorizations can be for per your business logic. If so, you should also call required validation method to check this authorization from your business logic layer. By doing this, even you don't check if users authorize(especially from background jobs), they can not perform this action if not authorized.

public class TaskService
{
    private readonly AuthorizationService _authorizationService;

    public TaskService(AuthorizationService authorizationService)
    {
        _authorizationService = authorizationService;
    }

    public void AssingTask(int taskId, int userId)
    {
        // you can perform this validation by attributes that properly generated for your design.
        // It is just sample
        // by this validate there is no user can do this action without having required right(s).
        this.Validate(Rights.AssignTask, userId);

        // do your assign business.
    }

    private void Validate(Rights right, int userId)
    {
        if (!_authorizationService.IsUserAuthorize(right, userId))
            throw new Exception("User has not right for this action.");
    }
}

Next step is better way to use this authorization methods on your monolith MVC layer. Again I highly recommend, create static extension methods and call it throughout the project for authorization. You can call this static extension methods by your User object from view as:

in view:

@if(User.IsAuthorize("Something"))
{
        <submit type = "button" text ="you can do this">
} 

and controller:

public class TaskController : Controller
{

    [CustomAuthorize(Right = Rights.AssignTask)]
    public ActionResult TaskAssing()
    {
        _taskService.AssignTask(userId);
    }
}

CustomAuthorize attribute:

[AttributeUsage(AttributeTargets.Method | AttributeTargets.Class, Inherited = true, AllowMultiple = false)]
public class CustomAuthorize : // ...
    {
    public Rights Right { get; set; }

    public void OnAuthorization(AuthorizationContext filterContext)
    {
        if (!AuthorizeExtension.IsAuthorize(filterContext.HttpContext.User.Identity))
        {
            redirect("UnAutorize");
        }

    }
}

static extension method:

public static class AuthorizeExtension
{
    public static bool IsAuthorize(this IPrincipal principal, Rights right)
    {
        return _authorizationService.IsUserAuthorize(right, principal.Identity.Id);
    }
}
Engineert
  • 929
  • 1
  • 6
  • 18