问题
I'm working on a Web Application implemented in ASP.NET MVC 5 with Web API 2.
I've implemented Integrated Windows Authentication by adding the following code to web.config:
<system.web>
<authentication mode="Windows" />
</system.web>
<system.webServer>
<security>
<authentication>
<windowsAuthentication enabled="true"/>
</authentication>
</security>
</system.webServer>
and by adding [Authorize]
annotation on top of my controllers.
Now, I'm asked to give access to some functionality based on the user's role. I've got a table where I hold the user permissions, but I don't know how I can create those roles, and associate the right permissions with them.
Any help would be appreciated.
Thanks in advance
[UPDATE]
Based on mason's answer, I've updated the code a bit.
Added the following line to web.config:
<roleManager defaultProvider="MyRoleProvider">
<providers>
<add
name="MyRoleProvider"
type="MyApp.App_Start.MyRoleProvider"
applicationName="My Tool" />
</providers>
</roleManager>
MyRoleProvider.cs:
public class MyRoleProvider : RoleProvider
{
private MyEntities db = new MyEntities();
public override void AddUsersToRoles(string[] usernames, string[] roleNames)
{
throw new NotImplementedException();
}
public override string ApplicationName
{
get;
set;
}
public override void CreateRole(string roleName)
{
throw new NotImplementedException();
}
public override bool DeleteRole(string roleName, bool throwOnPopulatedRole)
{
throw new NotImplementedException();
}
public override string[] FindUsersInRole(string roleName, string usernameToMatch)
{
throw new NotImplementedException();
}
public override string[] GetAllRoles()
{
throw new NotImplementedException();
}
public override string[] GetRolesForUser(string username)
{
throw new NotImplementedException();
}
public override string[] GetUsersInRole(string roleName)
{
throw new NotImplementedException();
}
public override void RemoveUsersFromRoles(string[] usernames, string[] roleNames)
{
throw new NotImplementedException();
}
public override bool IsUserInRole(string username, string roleName)
{
vUser user = db.vUsers.Where(u => u.UserName == username).First();
if (roleName == "User")
{
if (user.IsAllowedToView == true)
{
return true;
}
else
{
return false;
}
}
else if (roleName == "Administrator")
{
if (user.IsAllowedToSubmit == true)
{
return true;
}
else
{
return false;
}
}
else
{
return false;
}
}
public override bool RoleExists(string roleName)
{
if (roleName == "User" || roleName == "Administrator")
{
return true;
}
else
{
return false;
}
}
}
When I use [Authorize]
annotation on my controllers, and call HttpContext.Current.User.Identity.Name
it returns the ID that I use to login to my machine. (Part of AD) But, if I use [Authorize(Roles="User")], it keeps asking for my username and password again and again, and doesn't accept anything. I put breakpoints to every single method on MyRoleProvider class, but the program hasn't stopped at any which makes me think maybe it is not even calling the provider.
回答1:
Over each controller or Even each method inside the controller you can add your own custom authorization role.
[Authorize(Roles="Admin,Doctor")]
public class Investigation : Controller
{
}
NOTE: The roles must be written the same way it was inserted in the database.(Case senstive)
回答2:
If you wish to manage the roles from Active Directory you could always create Active Directory user groups for each particular role then use the [Authorize(Roles="{AD_GROUP_NAME}")]
annotation on top of your controller.
回答3:
In your specific situation (based on chat), it sounds like a role based concept is not appropriate for you, since your permissions are stored at the user level instead of the role level, and you're not allowed to change how that works due to company restrictions.
Instead, you should write your own filter that you can apply to your action methods. That filter should probably implement IAuthorizationFilter. That would allow you to do something like:
[RequirePermissions("Save")]
public ActionResult Save(Data date)
{
Database.Save(data);
return View("Success");
}
And probably the logic of verifying the user has that permission should be abstracted out to a common class so that you can also reuse the logic in views.
回答4:
public override string[] GetRolesForUser(string username)
{
var userrole = from role in db.roles
where username == role.userID
select role.role1;
if (userrole != null)
return userrole.ToArray();
else
return new string[] { };
//throw new NotImplementedException();
}
this function should be edited.
来源:https://stackoverflow.com/questions/32888418/how-to-use-roles-with-integrated-windows-authentication