這次的系統包含兩個子系統,所以做了一個分角色的身份驗證系統。
web.config <system.web>中設置
<authentication mode="Forms"> <!--驗證方式為窗體驗證--> <forms name=".ASPXAUTH" loginUrl="~/login.aspx" protection="All" timeout="60" path="/"></forms> </authentication> <authorization> <allow users="?"/> <!--根目錄網頁默認為所有用戶都能訪問--> </authorization>
外面添加
<!--設置admin目錄的訪問權限--> <location path="admin/Default.aspx"> <system.web> <authorization> <!--允許角色為admin的用戶可以訪問--> <allow roles="admin"/> <!--拒絕所有其他用戶訪問--> <deny users="*"/> <!--注意以上兩句的次序不能變--> </authorization> </system.web> </location> <!--設置index目錄的訪問權限--> <location path="index/Default.aspx"> <system.web> <authorization> <!--允許角色為stu的用戶可以訪問--> <allow roles="stu"/> <!--拒絕所有其他用戶訪問--> <deny users="*"/> <!--注意以上兩句的次序不能變--> </authorization> </system.web> </location>
login.aspx頁面身份驗證通過后
//創建一個身份驗證票 FormsAuthenticationTicket ticket = new FormsAuthenticationTicket(1, UserName, DateTime.Now, DateTime.Now.AddMinutes(30), false, UserRole); //將身份驗證票加密 string EncrTicket = FormsAuthentication.Encrypt(ticket); //創建一個Cookie HttpCookie myCookie = new HttpCookie(FormsAuthentication.FormsCookieName, EncrTicket); //將Cookie寫入客戶端 Response.Cookies.Add(myCookie); //跳轉到初始請求頁或默認頁面 Response.Redirect(FormsAuthentication.GetRedirectUrl(UserName, false));
golbal全局應用程序中添加代碼
void Application_AuthenticateRequest(object sender, EventArgs e) { //判斷正在請求頁的用戶的身份驗證信息是否為空 if (HttpContext.Current.User != null) { //判斷用戶是否已經進行了身份驗證 if (HttpContext.Current.User.Identity.IsAuthenticated) { //判斷當前用戶身份驗證的方式是否為Forms身份驗證方式 if (HttpContext.Current.User.Identity is FormsIdentity) { //獲得進行了Forms身份驗證的用戶標識 FormsIdentity UserIdent = (FormsIdentity)(HttpContext.Current.User.Identity); //從身份驗證票中獲得用戶數據 FormsAuthenticationTicket ticket = UserIdent.Ticket; string UserData = ticket.UserData; //string UserData = UserIdent.Ticket.UserData; //分割用戶數據得到用戶角色數組 string[] rolues = UserData.Split(','); //從用戶標識和角色組初始化GenericPrincipal類 HttpContext.Current.User = new System.Security.Principal.GenericPrincipal(UserIdent, rolues); } } } }
身份驗證設置完成后設置頁面跳轉
default頁面添加代碼
FormsIdentity id = (FormsIdentity)HttpContext.Current.User.Identity; if (id.Ticket.UserData.Contains("admin")) { //跳轉到訪問權限不夠的錯誤提示頁面 Response.Redirect("~/admin/Default.aspx", true); } else if (id.Ticket.UserData.Contains("stu")) { Response.Redirect("~/index/Default.aspx", true); } else Response.Redirect("~/login.aspx", true);
至此整個身份驗證完成。
vs上運行沒有問題,發布到IIS后報錯無法將類型為“System.Security.Principal.GenericIdentity”的對象強制轉換為類型“System.Web.Security.FormsIdentity”。
查找資料:
1、將網站應用程序池的托管管道模式由“集成”改為“經典”
2、網站“處理程序映射”添加”.aspx“請求路徑的可執行文件“C:\Windows\Microsoft.NET\Framework64\v4.0.30319\aspnet_isapi.dll”,或者將ISAPI中4.0的狀態改為可用狀態
以上網友成功解決問題的辦法在我這都不行。。。。。
login.aspx,golbal.asax,default.aspx,代碼調整過無數次,各種方法試過都無效。
===================================================================================================================
突發奇想將登陸ip改為 192.127.1.8080/login.aspx,。。。OK,終於不報錯誤界面了。
錯誤信息提示 無法將類型為“System.Security.Principal.GenericIdentity”的對象強制轉換為類型“System.Web.Security.FormsIdentity”,身份驗證出了問題,一直以為是iis對角色身份驗證有什么特殊設置,但最后發現時默認文檔沒有設置正確。
使用“默認文檔”功能頁可配置默認文檔的列表。如果用戶訪問您的網站或應用程序,但沒有指定文檔名),則可以配置 IIS 提供一個默認文檔,如 Default.htm。IIS 將返回與目錄中的文件名匹配的列表中的第一個默認文檔。
我的登陸頁面是login.aspx,IIS搜索返回default.aspx。default.aspx頁面中有一行代碼
FormsIdentity id = (FormsIdentity)HttpContext.Current.User.Identity;
(FormsIdentity)HttpContext.Current.User.Identity;中的formsIdentity表示“一個使用了forms身份驗證進行了身份驗證的用戶標識”,192.127.1.8080請求發送跳過了身份驗證界面,所以報錯。
解決:在默認文檔中“添加”login.aspx
(每次網站發布后都需要添加login默認文檔,所以想在代碼中定位到login頁面去,但發現無論是在default頁面進行設置跳轉,還是在golbal頁面添加設置,都會報錯,必須添加login頁面首先進行身份驗證)