16

What is everyone doing to handle security (retrieval and modification) of individual records in an ASP.NET MVC application? This application has a Service/Business layer and a Data Access layer that are completely separate from the Web user interface. I am already using the membership and roles providers to handle authentication and authorization for specific areas/features in my application, but now I need to secure individual records.

For example, say Bob can create and edit his own FooBar records. I want to ensure that other users cannot view or edit Bob's records. I want to protect against URL manipulation and/or programming mistakes. We may also want to allow Bob to share his FooBars with other users, allowing them to view but not edit his records.

There are several approaches I have come up with:

  • Do the security checks in the Data Access layer, directly in the retrieval and modification queries.
  • Check security in the Service layer, performing extra security queries before proceeding with the Business logic.
  • Create a Security layer that exists between the UI and the Service layer. The UI would make all requests through the Security layer.
  • Use aspect-oriented programming (AOP). Create security aspects and decorate the Service layer methods with security attributes.

I've done security in the Data Access layer (in the queries) in previous projects, and it always turns into a mess. I would like to know what everyone else is doing, and what frameworks you are using to help you (AOP frameworks.)

3 Answers 3

2

I always take 2nd and/or 3rd of your approaches - an explicit security layer somewhere between the UI and logic handlers.

AOP sounds like a way to completely lose control over the code and the security in DAL sounds like a wrong approach as it mixes up different responsibilities.

Sign up to request clarification or add additional context in comments.

Comments

2

I think putting logic everywhere might be a problem. I am having similar situation. Let me explain how I am handling it.

public class FooBarController : Controller { //this is easy as compared to edit [Authorized] public ActionResult Create() { } [AjaxAuthorize(Roles = "Administrator")] public ActionResult Edit(int id) { } } public class AjaxAuthorizeAttribute : AuthorizeAttribute { public override void OnAuthorization(AuthorizationContext filterContext) { var id = filterContext.RouteData.Values["id"]; // Here you can check if the id belongs to logged in user var content = SomeRepository.GetById(id); if (contet.OwnerId=LoggedInUser.Id) return; //otherwise check if logged in user is from some Admin or other role. string redirectPage = "/account/logon"; var roles = base.Roles.Trim().Split(','); bool CanAccess = false; //If no role is there if (base.Roles.Equals(string.Empty) || roles.Count() == 0) { CanAccess = true; } else { foreach (var item in roles) { CanAccess = filterContext.HttpContext.User.IsInRole(item); if (CanAccess) break; } } var request = filterContext.RequestContext.HttpContext.Request; if (request.IsAjaxRequest()) { if (!(request.IsAuthenticated && CanAccess)) { filterContext.Result = new AjaxAwareRedirectResult(redirectPage); return; } } base.OnAuthorization(filterContext); } } public class AjaxAwareRedirectResult : RedirectResult { public AjaxAwareRedirectResult(string url) : base(url) { } public override void ExecuteResult(ControllerContext context) { if (context.RequestContext.HttpContext.Request.IsAjaxRequest()) { string destinationUrl = UrlHelper.GenerateContentUrl(Url, context.HttpContext); JavaScriptResult result = new JavaScriptResult() { Script = "window.location='" + destinationUrl + "';" }; result.ExecuteResult(context); } else base.ExecuteResult(context); } } 

Now you can allowing Editing of the content either by the owner or by the administrator. I am calling this Attribute as Ajax, because it will handle AjaxRequest also. I hope this helps.

Regards

Parinder

Comments

0
public class Entity { public Right[] Rights { get; set; } } public class Right { public User user {get;set;} public Permission[] permissions {get;set;} } public class Foo : Entity { } public class Bar : Entity { } 

In the above approach there is a base class Entity which store the rights a particular user has over that entity. Inherit all the classes you want to secure from Entity class.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.