今天把源代碼貼出來
…
按照代碼再加點解釋。
?
1
)首先建立管理用戶表,其中
UserPopedom
記錄用戶的權限字符,其實也就是一些
JSP
或者
ACTION
的文件名:
CREATE TABLE [dbo].[AdminUser] (
?????? [UserID] [varchar] (50) COLLATE Chinese_PRC_CI_AS NULL ,
?????? [UserName] [varchar] (50) COLLATE Chinese_PRC_CI_AS NULL ,
?????? [UserPass] [varchar] (50) COLLATE Chinese_PRC_CI_AS NULL ,
?????? [UserPopedom] [text] COLLATE Chinese_PRC_CI_AS NULL
) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
2
)按照上面的表格建立該用戶的對象
package com.wake.bean;
?
public class AdminUser {
???
??? private String UserID;
??? private String UserName;
??? private String UserPass;
??? private String UserPopedom;
???
??? public String getUserID() {
?????????? return UserID;
??? }
??? public void setUserID(String userID) {
?????????? UserID = userID;
??? }
??? public String getUserName() {
?????????? return UserName;
??? }
??? public void setUserName(String userName) {
?????????? UserName = userName;
??? }
??? public String getUserPass() {
?????????? return UserPass;
??? }
??? public void setUserPass(String userPass) {
?????????? UserPass = userPass;
??? }
??? public String getUserPopedom() {
?????????? return UserPopedom;
??? }
??? public void setUserPopedom(String userPopedom) {
?????????? UserPopedom = userPopedom;
??? }
}
3
)對整個后臺的控制我這里分為了兩部分,一部分是欄目的顯示控制,一部分是資源(頁面)的操作控制。
其中欄目的顯示控制解釋為:以新聞欄目為例,如果某用戶沒有新聞欄目的任何管理權限(增、改、刪、申等),那么在后臺的管理菜單中將不顯示新聞欄目。否則,只要某用戶擁有其中任何一個權限,新聞欄目則顯示。這里要掌握的要領是,所有和新聞權限相關的頁面命名必須以
News
打頭,這樣將來決定顯示與否就以該用戶的權限字符中是否能找到
News
為依據。該功能的實現我寫了
Bean
來判斷。如下:
package com.wake.util;
?
import java.util.Map;
?
import com.opensymphony.xwork.ActionContext;
import com.wake.bean.AdminUser;
?
public class PopedomValidate {
???
??? public static boolean UserPopedomValidate(String pstr){
?????????? Map session = ActionContext.getContext().getSession();
?????????? AdminUser auser = (AdminUser)session.get("auser");
?????????? if(auser==null||auser.equals("")){
????????????????? return false;
?????????? }
?????????? else{
????????????????? if(auser.getUserPopedom().indexOf(pstr)!=-1)
???????????????????????? return true;
?????????? }
?????????? return false;
??? }
?
}
在頁面中使用如下判斷(我是在
WEBWORK
中實現),也可在
JSP
中直接調用!
<%@
taglib
uri
=
"webwork"
prefix
=
"ww"
%>
<
ww:bean
name
=
"'com.wake.util.PopedomValidate'"
id
=
"pd"
/>
<
ww:if
test
=
'#pd.UserPopedomValidate("News")'
>
新聞欄目
<
br
>
</
ww:if
>
對于資源(頁面)的操作控制我是使用
Filter
來進行控制的,
Filter
源碼如下。
?
package com.wake.util;
?
import java.io.IOException;
?
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
?
import com.wake.bean.AdminUser;
?
/**
?* @author Administrator
?*
?*/
public class PopedomControl extends HttpServlet implements Filter {
??? /**
???
?*
???
?*/
??? private FilterConfig filterConfig;
??? private static final long serialVersionUID = -4275105240038370264L;
?
??? /*
???
?*
(非
Javadoc
)
???
?*
???
?* @see javax.servlet.Filter#init(javax.servlet.FilterConfig)
???
?*/
??? public void init(FilterConfig arg0) throws ServletException {
??? }
?
??? /*
???
?*
(非
Javadoc
)
???
?*
???
?* @see javax.servlet.Filter#doFilter(javax.servlet.ServletRequest,
???
?*????? javax.servlet.ServletResponse, javax.servlet.FilterChain)
???
?*/
??? public void doFilter(ServletRequest request, ServletResponse response,
?????????? FilterChain filterChain) {
?
?????? HttpServletRequest servletRequest = (HttpServletRequest) request;
?????? HttpServletResponse servletResponse = (HttpServletResponse) response;
?????? HttpSession session = servletRequest.getSession();
?????? //
獲取當前頁面文件名
?????? String url = servletRequest.getRequestURI();
?????? url = url.substring(url.lastIndexOf("/") + 1, url.length());
??????
?????? try {
?????????? //
排除后臺不作權限控制的頁面名
?????????? String exclude= "adminlogin.action,login.jsp,Message.jsp,loginout.jsp";
???
?????? if(exclude.indexOf(url)==-1){
????????????? //
獲取網站訪問根目錄
????????????? String accessPath = servletRequest.getContextPath();
????????????? //
用當前頁面文件名與用戶權限字符比較
????????????? AdminUser adminuser = (AdminUser) session.getAttribute("auser");
????????????? if (adminuser == null) {
????????????????? servletResponse.sendRedirect(accessPath + "/admin/login.jsp");
????????????? }else if(adminuser.getUserPopedom().indexOf(url)==-1){
????????????????? servletResponse.sendRedirect(accessPath + "/admin/Message.jsp");
????????????? }
?????????? }
?????? } catch (Exception sx) {
?????????? sx.printStackTrace();
?????? }
??????
?????? try {
?????????? filterChain.doFilter(request, response);
?????? } catch (ServletException sx) {
?????????? filterConfig.getServletContext().log(sx.getMessage());
?????? } catch (IOException iox) {
?????????? filterConfig.getServletContext().log(iox.getMessage());
?????? }
??? }
?
??? public void destroy() {
??? }
?
}
WEB.XML
關于過濾器配置
???
<
filter
>
??????
<
filter-name
>
popedomcontrol
</
filter-name
>
??????
<
filter-class
>
com.wake.util.PopedomControl
</
filter-class
>
???
</
filter
>
???
<
filter-mapping
>
??????
<
filter-name
>
popedomcontrol
</
filter-name
>
??????
<
url-pattern
>
/admin/*
</
url-pattern
>
???
</
filter-mapping
>
?
這樣不知道大家看明白沒有
…
?
這次這個簡單的權限設計從開始到完成斷斷續續用了將近
3
天的時間,一切都是在摸索中進行。其實上面的設計思路經過優化和復雜化也可以設計為符合
RBAC
規范的例子。那需要我們在用戶和權限之間再加一個基本的角色進去。這樣用戶對應的是角色,而角色去對應權限。至于其它的就由我們自己自由發揮了呵呵,這次關于權限的試驗就到此了,讓大家見笑了。