I am working on a content management system , where i have a controller that display all the articles that are assigned to the current login user for his review, then the user can either approve or reject this article. To make sure that the user only sees the articles that are assigned to him i wrote the following query:-
public IQueryable<Article> MyApproval()
{
Guid id = (Guid)Membership.GetUser().ProviderUserKey;
return from article in db.Articles
where article.Approval_ID == id && article.Article_status_ID == 1 // 1 represents new articles in Article_status table
orderby article.Article_ID descending
select article;
}
But i found that the user might manually modify the URL and change the article id to an article that he is not assigned to and then he can approve or reject it; so i add the following check before the edit action method
[Authorize]
public ActionResult Edit(int id)
{
Article articleapproval = articletyperepository.GetArticle(id);
if (!articleapproval.Isapproval(User.Identity.Name))
return View(“InvalidOwner”);
else
{
articleapproval.Published_Date = DateTime.Now;
return View(articleapproval);}
}
}
So i have the following three questions:-
-
will the check on the controller level prevent the user from modifying the URL and accessing an article that he is not the assigned for
-
Should i add the below check on the POST version of the edit action method also (in addtion to the GET version), or it will be considered as unnecessary check?
if (!articleapproval.Isapproval(User.Identity.Name)) return View(“InvalidOwner”); -
what is better to pass the
User.Identity.Nameto the helper method (as i am currently doing) ? or to modify the helper method to generate theUser.Identity.Nameinside it as follow?public partial class Article { public bool Isapprova () { return HostedBy.Equals(User.Identity.Name, StringComparison.OrdinalIgnoreCase);} } }
Yes
You should check both GET and POST
The helper method does not need to know as to how to retrieve the current user’s name. Your implementation is fine.