我一直在使用MVCSiteMap设置我的菜单我有这样的节点:MVCSiteMap节点Requring多重角色
<mvcSiteMapNode title="Courses Form" controller="Booking" action="Course" roles="CORLIC, VIEWCOBO"/>
我试图强制执行,这点必须有角色“CORLIC” AND“VIEWCOBO”为它是可见的,但当然这意味着如果用户具有上述任何一个,它将被显示。
这可能吗?
谢谢。
我一直在使用MVCSiteMap设置我的菜单我有这样的节点:MVCSiteMap节点Requring多重角色
<mvcSiteMapNode title="Courses Form" controller="Booking" action="Course" roles="CORLIC, VIEWCOBO"/>
我试图强制执行,这点必须有角色“CORLIC” AND“VIEWCOBO”为它是可见的,但当然这意味着如果用户具有上述任何一个,它将被显示。
这可能吗?
谢谢。
roles属性用于与ASP.NET的互操作性,不应仅用于MVC专用应用程序。
对于MVC,如果您已经在控制器操作中定义了AuthorizeAttribute,则MvcSiteMapProvider将自动选取它们并相应地隐藏匹配节点,如果启用了security trimming。
[Authorize]
public ActionResult Course()
{
return View();
}
[Authorize]
[HttpPost]
public ActionResult Course(CourseModel model)
{
if (ModelState.IsValid)
{
// Implementation omitted
}
// If we got this far, something failed, redisplay form
return View(model);
}
默认AuthorizeAttribute接受的角色,但它在为角色属性相同的方式工作 - 也就是说,用户是会导致它成功的任何角色。
但是,您可以自己继承AuthorizeAttribute并覆盖IsAuthorized method以根据需要更改逻辑。
public class SpecialAuthorizeAttribute : AuthorizeAttribute
{
private string _requiredRoles;
private string[] _requiredRolesSplit = new string[0];
/// <summary>
/// Gets or sets the required roles. The user must be a member of all roles for it to succeed.
/// </summary>
/// <value>
/// The roles string.
/// </value>
/// <remarks>Multiple role names can be specified using the comma character as a separator.</remarks>
public string RequiredRoles
{
get { return _requiredRoles ?? String.Empty; }
set
{
_requiredRoles = value;
_requiredRolesSplit = SplitString(value);
}
}
/// <summary>
/// Determines whether access for this particular request is authorized. This method uses the user <see cref="IPrincipal"/>
/// returned via <see cref="HttpRequestContext.Principal"/>. Authorization is denied if the user is not authenticated,
/// the user is not in the authorized group of <see cref="Users"/> (if defined), or if the user is not in any of the authorized
/// <see cref="Roles"/> (if defined).
/// </summary>
/// <param name="actionContext">The context.</param>
/// <returns><c>true</c> if access is authorized; otherwise <c>false</c>.</returns>
protected override bool IsAuthorized(HttpActionContext actionContext)
{
if (actionContext == null)
{
throw new ArgumentNullException("actionContext");
}
IPrincipal user = actionContext.ControllerContext.RequestContext.Principal;
if (user == null || user.Identity == null || !user.Identity.IsAuthenticated)
{
return false;
}
// Ensure all of the roles in RequiredRoles are present.
if (_requiredRolesSplit.Length > 0 && !_requiredRolesSplit.All(user.IsInRole))
{
return false;
}
// Call the base class to check the users and roles there.
return base.IsAuthorized(actionContext);
}
/// <summary>
/// Splits the string on commas and removes any leading/trailing whitespace from each result item.
/// </summary>
/// <param name="original">The input string.</param>
/// <returns>An array of strings parsed from the input <paramref name="original"/> string.</returns>
internal static string[] SplitString(string original)
{
if (String.IsNullOrEmpty(original))
{
return new string[0];
}
var split = from piece in original.Split(',')
let trimmed = piece.Trim()
where !String.IsNullOrEmpty(trimmed)
select trimmed;
return split.ToArray();
}
}
然后,您可以指定使用新属性需要哪些角色。
[SpecialAuthorize(RequiredRoles = "CORLIC, VIEWCOBO")]
public ActionResult Course()
{
return View();
}
[SpecialAuthorize(RequiredRoles = "CORLIC, VIEWCOBO")]
[HttpPost]
public ActionResult Course(CourseModel model)
{
if (ModelState.IsValid)
{
// Implementation omitted
}
// If we got this far, something failed, redisplay form
return View(model);
}
另一个可能的选择是使用FluentSecurity为shown here。对于FluentSecurity v2.0与MvcSiteMapProvider一起使用,您需要将HandleSecurityAttribute code复制到您的项目中,并将其更改为从AuthorizeAttribute而不是Attribute继承,然后按照FluentSecurity文档中的说明使用它。