【Struts2进阶】Struts2拦截器实现基于Url的权限管理

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/u010028869/article/details/50904246

Struts2的拦截器只能拦截Action,拦截器是AOP的一种实现方式,可以使我们的系统架构更松散(耦合度低),可以插拔,容易互换,代码不改变的情况下很容易满足客户需求。

项目的权限管理模块就使用到了Struts2的拦截器,原理是这样的,我们来自定义一个拦截器,拦截所有的Action请求,对用户的登录状态和权限信息进行判断。如果用户为登录状态且有足够的权限,则继续访问;若未登录,则为其跳转到登录页面,若无足够权限,则跳转到无权访问页面。

下面来看看具体实现:


自定义拦截器CheckPrivilegeInterceptor

package cn.itcast.oa.util;

import cn.itcast.oa.domain.User;

import com.opensymphony.xwork2.ActionContext;
import com.opensymphony.xwork2.ActionInvocation;
import com.opensymphony.xwork2.interceptor.AbstractInterceptor;

public class CheckPrivilegeInterceptor extends AbstractInterceptor {

    public String intercept(ActionInvocation invocation) throws Exception {
        // 获取信息
        User user = (User) ActionContext.getContext().getSession().get("user"); // 当前登录用户
        String namespace = invocation.getProxy().getNamespace();
        String actionName = invocation.getProxy().getActionName();
        String privUrl = namespace + actionName; // 对应的权限URL,用户要访问的URL

        // 如果未登录
        if (user == null) {
            if (privUrl.startsWith("/user_login")) { // "/user_loginUI", "/user_login"
                // 如果是去登录,就放行
                return invocation.invoke();
            } else {
                // 如果不是去登录,就转到登录页面
                return "loginUI";
            }
        }
        // 如果已登 录,就判断权限
        else {
            if (user.hasPrivilegeByUrl(privUrl)) {
                // 如果有权限,就放行
                return invocation.invoke();
            } else {
                // 如果没有权限,就转到提示页面
                return "noPrivilegeError";
            }
        }
    }
}


在拦截器中会通过session信息判断用户是否登录,通过自己写的hasPrivilegeByUrl()方法判断是否有相应的访问权限。


配置拦截器

<struts>
    <!-- 当struts.xml配置文件发生修改,会立刻加载,在生产环境下最好不要配置 -->
    <constant name="struts.configuration.xml.reload" value="true"/>
    <!-- 会提供更加友好的提示信息 -->
    <constant name="struts.devMode" value="true"/>
    <!-- 需要继承struts-default包,这样就拥有的最基本的功能 -->
    <package name="struts2" extends="struts-default">
            <interceptors>
                <!-- 声明拦截器 -->
                <interceptor name="checkPrivilege" class="cn.itcast.oa.util.CheckPrivilegeInterceptor"></interceptor>

                <!-- 定义自己的拦截器栈 -->
                <interceptor-stack name="myInterceptorStack">
                    <interceptor-ref name="checkPrivilege"></interceptor-ref>
                                                 <!-- defaultStack:Struts2的默认拦截器栈 -->
                    <interceptor-ref name="defaultStack"></interceptor-ref>
                </interceptor-stack>
            </interceptors>


                 <!-- 定义为缺省拦截器,所有的Action都会得到使用 -->
                 <default-interceptor-ref name="myInterceptorStack"/>   


        <!-- 全局的Result配置 -->
        <global-results>
            <result name="loginUI">/WEB-INF/jsp/userAction/loginUI.jsp</result>
            <result name="noPrivilegeError">/noPrivilegeError.jsp</result>
        </global-results>

        <!--其他Action -->
                .
                .
                .

    </package>
</struts>


首先将自定义的拦截器配置好,另外因为咱们自定了拦截器,会导致缺省拦截器会失效,必须显示引用Struts2默认的拦截器即defaultStack。

然后重新定义缺省拦截器<default-interceptor-ref>,对所有的Action都有效,替换defaultStack。

经过这两步配置后,自定义的拦截器就能使用了。

扫描二维码关注公众号,回复: 3776311 查看本文章

小结

整个拦截器体现了责任链模式,Filter也体现了责任链模式,后面会讲到Shiro的过滤器链,也是这个意思。

拦截器的执行原理就是,在ActionInvocation中有一个成员变量Iterator,这个Iterator中保存了所有的拦截器,每次都会取得Iterator进行next,执行invocation.invoke()方法,如果找到了拦截器就会执行拦截器内容,找不到的话就继续往下走,执行自定义的Action方法,都执行完拦截器出栈。

本篇主要讲解的是如何使用Struts2拦截器,关于权限管理的具体流程,后面会详细讲到。

猜你喜欢

转载自blog.csdn.net/u010028869/article/details/50904246
今日推荐