Currently I'm doing a check :
#if(this.User.Identity.Name=="DOMAIN\\USERID"){
This works great but I'd like to have multiple users(2-3) to check for. I'd also like to not have it hard coded. Is there a way to do this in the web.config or in a database?
You could add a list in the config...User1,User2 etc and then use linq and .Any() against this list?
var users = "user1,user2,user3".Split(','); //list will come from your config
bool result = users.Any(u => u == this.User.Identity.Name);
Also, since you're using MVC, if you want to use authorization for controllers etc, you can use the [Authorize] attribute. See this SO link too Authorize attribute in ASP.NET MVC
Maybe use roles instead then add the relevant users to that role? This would make it easier to expand on in the future, plus you don't have to hard code a list of users.
Related
I have to make vanity urls for an already existing site. The requirements are:
The existing controllers are a kind of hierarchical structure and can't go away or be overridden in any way. Examples: domain.com/Dog/vanity and domain.com/Cat/vanity.
Keep existing actions. Any existing actions must take priority so that the page for that action is not stomped on by the vanity url.
take future pages and actions into account so that the above requirement is met (a new vanity url is ignored and the action/view executed instead)
To date, I have tried various solutions with routing that allow me to have domain.com/vanity which is nice but the marketing guys don't like because of the different departments within the company. I've tried routing which will override the existing actions and treats them all as vanities (also not feasible). I've a solution in place that programmatically deals with the url that was requested and redirects to a page that actually exists but this is not scalable in any way.
So far, I know that the vanity portion can be treated as a parameter to the action so that I can fire off the default page in the route (Index) but this is, so far, doesn't preserve the structure.
TL;DR: I need to have a solution that allows for domain/controller/vanity structure while also allowing domain/controller/action
Using AttributeRouting for MVC4 you can accomplish a working solution until you ramp up the replacement project. It'll allow you to keep existing routes while adding new, custom ones with little impact.
[Route("my-vanity/is-cool/post/{id}")]
public ActionResult Index(int id)
{
}
The important part is to remember priority, so you write routes that don't overwrite/are overwritten by existing routes. You can steer this to some degree with properties on the attribute. Below is just an example that will put the added route last in priority for the entire site.
[Route("my-vanity/is-cool", SitePrecedence = -1)]
public ActionResult Index()
{
}
ASP.NET WebApi2 have built in support for attribute routing. With it you can define URL's in whatever way you like (instead of following the /controller/action pattern)
http://www.asp.net/web-api/overview/web-api-routing-and-actions/attribute-routing-in-web-api-2
I am designing ASP.NET WEB API service with two interfaces. First interface is read-only and second one is admin interface (to be used with MVC app) with full CRUD support. Does anyone know where I can get more information on such setup, any tutorials, walk thought, sample design document?
Also does it worth splitting these into two interfaces or keep them in same? But problem is that in read-only I expose 2-3 properties for every object while for admin there are 10-15?
Similar setup for WCF or design spec will do.
If I understand what your wanting to do, may I suggest rather than having one URL, i.e. \dataStuff\dataView split off into another view, maybe \dataStuff\edit\ which only admin's have access to, can be done like so:
[Authorize(Roles = "Administrators")]
public ActionResult edit()
{
return View();
}
then next to each data element that your viewing add the following to ONLY admin's through use of User.IsInRole
#foreach (var item in Model.dataTable)
{
#*
write a value from the data table here
*#
#Html.ActionLink("edit", "edit").If(User.IsInRole("Administrators"))
<br/>
}
obviously you don't have to display your data like this, I'm just showing that you add to the end of each element of the database an edit ActionLink IF the user is admin.
This allows your admin to view data like a user and also have the added functionality they need. Code re-use is better than a single view which has two states, Admin and non Admin.
Sorry if this isn't the best explanation, fairly new to MVC
Seems like this concept is sometimes called CQRS.
Sample: http://martinfowler.com/bliki/CQRS.html
Just curious what would be the best way to do this?
used to using
if (User.IsInRole("Administrator"))
with an older program of mine,
Using the new Kendo templete( new to me ) for MVC4-VS2012 Projects it created everything w/o simplemembership, so i wrote my own login system with help of some youtube videos and documentations.
It is very flexible and works, just curious on how I can check if a user is in a Roll Via A view ( like if (User.IsInRole("Administrator")) ) would have done. And or the best way to do so ( possibly in controller )
You can continue to use User.IsInRole(""), you simply need to set HttpContext.User with the correct principal that has a list of roles.
You can create your own Authorization Attribute that would take care of this:
var websiteRoles = userRepo.GetRoles(HttpContext.User.Identity.Name);
var identity = filterContext.HttpContext.User.Identity as FormsIdentity;
filterContext.HttpContext.User = new System.Security.Principal.GenericPrincipal(identity, websiteRoles.ToArray());
Follow up:
Your GetRoles() method can be implemented any way you like, you simply need to have a list of roles that the user belongs to. You will use this list to create the Principal object to set the User to.
Using this approach will allow you to use User.IsInRole()
Is there a way to retrieve all access rules from a specific Role?
As roles are just flagged at the top of an action or on top of the whole class I canĀ“t find a way to retrieve this information unless I read and parse the whole file and after that find a way to link this [authorization] tag to a group.
Thanks
No there is no builtin way. Its even impossible, because you might check for Roles in your code (actions/views) as well.
And how should the list of access rules be returned?
For example, how should an algorithm return / name this access rule in a view:
#if(User.IsInRole("SomeRole") {
<div>
Show some html only visible for users in SomeRole
</div>
}
You have to administer the list of your application defined access rules by yourself - i list will be very specific for your app.
Of cause, when you just use the Authorize attribute, you could generate a list of action methods accessible for a given role by reflecting over all controller classes.
Currently I use [Authorize(Roles = ".....")] to secure my controller actions on my ASP.NET MVC 1 app, and this works fine. However, certain search views need to have buttons that route to these actions that need to be enabled/disabled based on the record selected on the search list, and also the security privs of the user logged in.
Therefore I think I need to have a class accessing a DB table which cross-references these target controller/actions with application roles to determine the state of these buttons. This will, obviously, make things messy as privs will need to be maintained in 2 places - in that class/DB table and also on the controller actions (plus, if I want to change the access to the action I will have to change the code and compile rather than just change a DB table entry).
Ideally I would like to extend the [Authorize] functionality so that instead of having to specify the roles in the [Authorize] code, it will query the security class based on the user, controller and action and that will then return a boolean allowing or denying access. Are there any good articles on this - I can't imagine it's an unusual thing to want to do, but I seem to be struggling to find anything on how to do it (could be Monday-morning brain). I've started some code doing this, looking at article http://schotime.net/blog/index.php/2009/02/17/custom-authorization-with-aspnet-mvc/ , and it seems to be starting off ok but I can't find the "correct" way to get the calling controller and action values from the httpContext - I could possibly fudge a bit of code to extract them from the request url, but that doesn't seem right to me and I'd rather do it properly.
Cheers
MH
I found this on another forum and so will post it here in case anyone finds it useful. Note that how you do this changes depending on whether you are using MVC 1 or 2
the class you create needs to implement
public void OnAuthorization(AuthorizationContext filterContext)
and then you can use
string controllerName = filterContext.RouteData.Values["controller"].ToString();
and the same, substituting "action" for "controller" (make sure you check for nulls in these values first). In MVC 2 this can be changed to filterContext.ActionDescriptor.ActionName and .ActionDescriptor.ControllerDescriptor.ControllerName and you won't have to check for nulls