Могу ли я скрыть/показать asp: пункты меню на основе роли?
Можно ли скрывать определенные пункты меню в элементе управления asp:Menu
на основе роли?
<asp:Menu ID="mTopMenu" runat="server" Orientation="Horizontal" />
<Items>
<asp:MenuItem Text="File">
<asp:MenuItem Text="New Project" />
<asp:MenuItem Text="Release Template" NavigateUrl="~/Release/ReleaseTemplate.aspx" />
<asp:MenuItem Text="Release Schedule" NavigateUrl="~/Release/ReleaseSchedule.aspx" />
<asp:MenuItem Text="Roles" NavigateUrl="~/Admin/AdminRoles.aspx" />
</asp:MenuItem>
</Items>
</asp:Menu>
Как я могу сделать один из этих элементов видимым только для пользователей в роли администратора?
Я использую поставщик роли asp.net.
Ответы
Ответ 1
Вы можете привязать элементы меню к карте сайта и использовать атрибут ролей. Для этого вам необходимо включить обрезку безопасности в вашем Web.Config. Это самый простой способ.
Обзор навигации по сайту:
http://msdn.microsoft.com/en-us/library/e468hxky.aspx
Информация о настройке безопасности:
http://msdn.microsoft.com/en-us/library/ms178428.aspx
Информация о привязке SiteMap:
http://www.w3schools.com/aspnet/aspnet_navigation.asp
Хороший учебник/обзор здесь:
http://weblogs.asp.net/jgalloway/archive/2008/01/26/asp-net-menu-and-sitemap-security-trimming-plus-a-trick-for-when-your-menu-and-security-don-t-match-up.aspx
Другой вариант, который работает, но менее идеален, заключается в использовании элемента управления loginview, который может отображать элементы управления на основе роли. Это может быть самый быстрый (но наименее гибкий/эффективный) вариант. Вы можете найти руководство здесь: http://weblogs.asp.net/sukumarraju/archive/2010/07/28/role-based-authorization-using-loginview-control.aspx
Ответ 2
Вы можете удалить ненужные пункты меню в Page_Load, например:
protected void Page_Load(object sender, EventArgs e)
{
if (!Roles.IsUserInRole("Admin"))
{
MenuItemCollection menuItems = mTopMenu.Items;
MenuItem adminItem = new MenuItem();
foreach (MenuItem menuItem in menuItems)
{
if (menuItem.Text == "Roles")
adminItem = menuItem;
}
menuItems.Remove(adminItem);
}
}
Я уверен, что есть более простой способ найти нужный элемент для удаления, но этот работает. Вы также можете добавить все нужные пункты меню в метод Page_Load, а не добавлять их в разметку.
Ответ 3
Я предпочитаю использовать метод FindItem и использовать путь значения для определения местоположения элемента. Убедитесь, что свойство PathSeparator в меню соответствует тому, что вы используете в параметре FindItem.
protected void Page_Load(object sender, EventArgs e)
{
// remove manage user accounts menu item for non-admin users.
if (!Page.User.IsInRole("Admin"))
{
MenuItem item = NavigationMenu.FindItem("Users/Manage Accounts");
item.Parent.ChildItems.Remove(item);
}
}
Ответ 4
Это лучше всего сделать в MenuItemDataBound.
protected void NavigationMenu_MenuItemDataBound(object sender, MenuEventArgs e)
{
if (!Page.User.IsInRole("Admin"))
{
if (e.Item.NavigateUrl.Equals("/admin"))
{
if (e.Item.Parent != null)
{
MenuItem menu = e.Item.Parent;
menu.ChildItems.Remove(e.Item);
}
else
{
Menu menu = (Menu)sender;
menu.Items.Remove(e.Item);
}
}
}
}
Поскольку в примере использовался NavigateUrl, он не зависит от языка и работает на сайтах с локализованными картами сайтов.
Ответ 5
Метод SIMPLE может быть не лучшим для всех случаев
<%
if (Session["Utype"].ToString() == "1")
{
%>
<li><a href="../forms/student.aspx"><i class="fa fa-users"></i><span>STUDENT DETAILS</span></a></li>
<li><a href="../forms/UserManage.aspx"><i class="fa fa-user-plus"></i><span>USER MANAGEMENT</span></a></li>
<%
}
else
{
%>
<li><a href="../forms/Package.aspx"><i class="fa fa-object-group"></i><span>PACKAGE</span></a></li>
<%
}
%>
Ответ 6
Чтобы удалить MenuItem
из ASP.net NavigationMenu
с помощью Value
:
public static void RemoveMenuItemByValue(MenuItemCollection items, String value)
{
MenuItem itemToRemove = null;
//Breadth first, look in the collection
foreach (MenuItem item in items)
{
if (item.Value == value)
{
itemToRemove = item;
break;
}
}
if (itemToRemove != null)
{
items.Remove(itemToRemove);
return;
}
//Search children
foreach (MenuItem item in items)
{
RemoveMenuItemByValue(item.ChildItems, value);
}
}
и вспомогательное расширение:
public static RemoveMenuItemByValue(this NavigationMenu menu, String value)
{
RemoveMenuItemByValue(menu.Items, value);
}
и использование образца:
navigationMenu.RemoveMenuItemByValue("UnitTests");
Примечание. Любой код выпущен в общедоступном домене. Не требуется атрибуция.
Ответ 7
Попробуйте следующее:
protected void Menu1_DataBound(object sender, EventArgs e)
{
recursiveMenuVisit(Menu1.Items);
}
private void recursiveMenuVisit(MenuItemCollection items)
{
MenuItem[] itemsToRemove = new MenuItem[items.Count];
int i = 0;
foreach (MenuItem item in items)
{
if (item.NavigateUrl.Contains("Contact.aspx"))
{
itemsToRemove[i] = item;
i++;
}
else
{
if (item.ChildItems.Count > 0) recursiveMenuVisit(item.ChildItems);
}
}
for(int j=0; j < i; j++)
{
items.Remove(itemsToRemove[j]);
}
}
Ответ 8
Вам просто нужно удалить родительское меню в событии init страницы.
Protected Sub navMenu_Init(sender As Object, e As System.EventArgs) Handles navMenu.Init
'Remove the admin menu for the norms
Dim cUser As Boolean = HttpContext.Current.User.IsInRole("Admin")
'If user is not in the Admin role removes the 1st menu at index 0
If cUser = False Then
navMenu.Items.RemoveAt(0)
End If
End Sub
Ответ 9
Чтобы найти элементы меню в базе содержимого на основе ролей
protected void Page_Load(object sender, EventArgs e)
{
if (Session["AdminSuccess"] != null)
{
Menu mainMenu = (Menu)Page.Master.FindControl("NavigationMenu");
//you must know the index of items to be removed first
mainMenu.Items.RemoveAt(1);
//or you try to hide menu and list items inside menu with css
// cssclass must be defined in style tag in .aspx page
mainMenu.CssClass = ".hide";
}
}
<style type="text/css">
.hide
{
visibility: hidden;
}
</style>
Ответ 10
У меня есть мое меню на главной странице сайта. Я использовал функцию Page_Load(), чтобы сделать пункт меню "Admin" доступным только пользователям с ролью администратора.
using System;
using System.Linq;
using Telerik.Web.UI;
using System.Web.Security;
<telerik:RadMenu ID="menu" runat="server" RenderMode="Auto" >
<Items>
<telerik:RadMenuItem Text="Admin" Visible="true" />
</Items>
</telerik:RadMenu>
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
RadMenuItem item = this.menu.FindItemByText("Admin");
if (null != item)
{
if (Roles.IsUserInRole("Admin"))
{
item.Visible = true;
}
else
{
item.Visible = false;
}
}
}
}