【问题标题】:Skip Java Filter based on Condition根据条件跳过 Java 过滤器
【发布时间】:2015-01-21 17:19:10
【问题描述】:

我查看了How to skip a filter in the filter chain in java 并遵循了解决方案,但这没有帮助。

我的 web.xml 中有三个过滤器。 Struts 过滤器、自定义过滤器和 IAM 代理过滤器按此顺序排列。我想根据某些条件跳过 IAM 过滤器。我无法控制 IAM 过滤其外部代码和平。因此,当前端参数说用户类型是内部时,我需要调用 IAM 代理过滤器,否则我需要跳过此过滤器。

Web.xml

<?xml version="1.0" encoding="UTF-8"?>
<web-app 
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
xmlns="http://java.sun.com/xml/ns/javaee" 
xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" 
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" 
id="WebApp_ID" 
version="2.5">
<display-name>App</display-name>
<!-- Struts2 Filter -->
<filter>
    <filter-name>struts2</filter-name>
    <filter-class>org.apache.struts2.dispatcher.FilterDispatcher</filter-class>
</filter>
    <filter-mapping>
    <filter-name>struts2</filter-name>
    <url-pattern>*.action</url-pattern>
</filter-mapping>
 <!-- Custom App Filter for Handling Internal And External User-->
<filter>
   <filter-name>UserType</filter-name>
   <filter-class>com.App.web.filter.LoginFilter</filter-class>
</filter>
<filter-mapping>
   <filter-name>UserType</filter-name>
   <url-pattern>/*</url-pattern>
</filter-mapping>

<!-- IAM Filter for Internal Users only-->
<filter>
   <filter-name>Agent</filter-name>
   <filter-class>com.sun.identity.agents.filter.AmAgentFilter</filter-class>
</filter>
<filter-mapping>
   <filter-name>Agent</filter-name>
   <url-pattern>/*</url-pattern>
</filter-mapping>   

<welcome-file-list>
    <welcome-file>index.jsp</welcome-file>
</welcome-file-list>
<listener>
    <listener-class>org.apache.tiles.web.startup.TilesListener</listener-class>
</listener>
<listener> 
    <listener-class>com.App.init.InitListener</listener-class>
</listener>
<context-param>
    <param-name>org.apache.tiles.impl.BasicTilesContainer.DEFINITIONS_CONFIG</param-name>
    <param-value>/WEB-INF/tiles.xml</param-value>
</context-param>

<!-- Web Service -->
<servlet>
    <servlet-name>EventManagementWS</servlet-name>
    <servlet-class>com.App.eventmanagement.ws.EventManagementWS</servlet-class>
    <load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
    <servlet-name>EventManagementWS</servlet-name>
    <url-pattern>/EventManagementWS</url-pattern>
</servlet-mapping>
<resource-ref>
       <res-ref-name>url/ConfigProperty</res-ref-name>
       <res-type>java.net.URL</res-type>
       <res-auth>Container</res-auth>
       <res-sharing-scope>Shareable</res-sharing-scope>
</resource-ref>

我正在使用 RequestDispatcher#forward(),但我的 index.jsp 页面输出中没有任何内容,只是一个空白页面。 css 文件出现 404 错误。当我使用 Struts 标签时,它给出了错误

Uncaught exception created in one of the service methods of the servlet /index.jsp in application App. Exception created: The Struts dispatcher cannot be found.  This is usually caused by using Struts tags without the associated filter. Struts tags are only usable when the request has passed through its servlet filter, which initializes the Struts dispatcher needed for this tag.

所以我删除了 S 标签并使用了硬编码,但现在我在尝试包含的所有 css 中都出现 404 错误。

感觉前锋好像不行了。

Java 过滤器代码:

package com.App.web.filter;

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.HttpServletRequest;
import javax.servlet.http.HttpSession;

import org.apache.commons.lang.StringUtils;

import com.App.constant.Constant;
import com.App.init.WIMSInitListener;
import com.App.log.WIMSMessageLogger;

public class LoginFilter implements Filter{

FilterConfig _filterConfig = null;
@Override
public void destroy(){
    // TODO Auto-generated method stub

}

@Override
public void doFilter(ServletRequest request, ServletResponse response, 
       FilterChain filterChain) throws IOException, ServletException{
    // Check IAM is enabled
    if (InitListener.isIAMEnabled()){
        HttpSession session = httpRequest.getSession();
        String userType = (String) session.getAttribute(Constant.USER_TYPE);
        if(userType == null || "".equals(userType)){
            MessageLogger.putMessageLog("User type is null : First Request" + userType, getClass());
            userType = request.getParameter(Constant.USER_TYPE);
            session.setAttribute(Constant.USER_TYPE, userType);
            request.getRequestDispatcher(((HttpServletRequest)request).getServletPath() + 
                    StringUtils.defaultString(((HttpServletRequest)request).getPathInfo()))
                        .forward(request, response);

        }
        if("external".equals(userType)){
            MessageLogger.putMessageLog("External User" + userType, getClass());
            request.getRequestDispatcher(((HttpServletRequest)request).getServletPath() + 
                    StringUtils.defaultString(((HttpServletRequest)request).getPathInfo()))
                        .forward(request, response);

        }
        else if("internal".equals(userType)){
            MessageLogger.putMessageLog("Internal User" + userType, getClass());
            //IAM Filter com.sun.identity.agents.filter.AmAgentFilter
            filterChain.doFilter(request, response);
        }
   }
   //Its always External User
   else{
       MessageLogger.putMessageLog("User IAM Not Enabled", getClass());
       request.getRequestDispatcher(((HttpServletRequest)request).getServletPath() + 
               StringUtils.defaultString(((HttpServletRequest)request).getPathInfo()) )
                      .forward(request, response);

   }
}

@Override
public void init(FilterConfig filterConfig) throws ServletException{
    this._filterConfig = filterConfig;
} 
}

索引.jsp

<%@ page language="java" contentType="text/html; charset=ISO-8859-1"
pageEncoding="ISO-8859-1"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01     Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<title>App</title>
<link rel="stylesheet" type="text/css" media="screen"
href="/App/css/common.css" />
<link rel="stylesheet" type="text/css" media="screen"
href="/App/css/rcorp.css" />
<link rel="stylesheet" type="text/css" media="all"
href="/App/css/style.css" />
<link rel="stylesheet" type="text/css" media="all"
href="/App/css/rcorp.css" />
<link rel="stylesheet" type="text/css" media="all"
href="/App/css/default.css" />
<script type="text/javascript">
function selectUserType(){
var frm = document.forms["UserTypeForm"];
if(document.getElementById("userTypeInternal").checked){
    //frm.action='<s:url action="loginAction.action?usertype=internal" namespace="" />';
    frm.action='/App/loginAction.action?usertype=internal';
}
else{
    //frm.action='<s:url action="loginAction.action?usertype=external" namespace="" />';
    frm.action='/App/loginAction.action?usertype=external';
}   
frm.target='_parent';
frm.submit();
}
function checkUserType(){   
//var userType = '<s:property value="#session.usertype" />';
var userType = '<%= session.getAttribute("usertype") %>';
if(userType == 'internal'){
    //frm.action='<s:url action="loginAction.action?usertype=internal" namespace="" />';
    frm.action='/App/loginAction.action?usertype=internal';
    frm.target='_parent';
    frm.submit();
}
else if(userType == 'external'){
    //frm.action='<s:url action="loginAction.action?usertype=external" namespace="" />';
    frm.action='/App/loginAction.action?usertype=external';
    frm.target='_parent';
    frm.submit();
}
}
</script>
</head>
<body onload="javascript:checkUserType();">
<form method="POST" action="loginAction.action" name="UserTypeForm">
    <div id="display_option"
        style="DISPLAY: none; position: absolute; top: 40%; width: 100%;"
        align="center">
        <div class="rcorp-tbl">
            <div style="width: 340px;">
                <div style="border: 1px solid #6da6fe; padding: 5px;">
                    <table style="background-color: #f0f8ff;" cellspacing=2 border=0>
                        <tr>
                            <td class="t-cellsecnowrap">Select User type:</td>
                            <td>
                            <td class="t-cell">
                                <div id="wwgrp_systemType" class="wwgrp">
                                    <div id="wwctrl_systemType" class="wwctrl">
                                        <input type="radio" name="UserType" id="internal" value="internal" checked/>
                                            <label for="userTypeInternal">Internal User (Sydney Trains Users)</label>&nbsp; 
                                        <input type="radio" name="userType" id="external" value="external"/>
                                            <label for="userTypeExternal">External User</label>&nbsp;&nbsp;&nbsp;&nbsp;
                                        <input type="button" name="applyBtn" id="applyBtn" class="btn" value="Go" title="Go" onclick="javascript:selectUserType();"/>
                                    </div>
                                </div>
                            </td>
                        </tr>
                    </table>
                </div>
            </div>
        </div>
    </div>
</form>
</body>
</html>

【问题讨论】:

    标签: java jakarta-ee struts2 servlet-filters


    【解决方案1】:

    与其尝试在您的LoginFilter 中控制它,不如创建一个扩展com.sun.identity.agents.filter.AmAgentFilter 的新类并在您的web.xml 中配置它。你的课看起来像这样:

    public class CustomFilter extends AmAgentFilter {
        @Override
        public void init(FilterConfig filterConfig) throws ServletException {
            super.init(filterConfig);
        }
    
        @Override
        public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
            if (InitListener.isIAMEnabled()) {
                HttpSession session = httpRequest.getSession();
                String userType = (String) session.getAttribute(Constant.USER_TYPE);
                if ("internal".equals(userType)) {
                    super.doFilter(servletRequest, servletResponse, filterChain);
                }
            }
            filterChain.doFilter(servletRequest, servletResponse);
        }
    
        @Override
        public void destroy() {
            super.destroy();
        }
    }
    

    super.doFilter() 调用将仅在满足该 if 块中的条件时执行AmAgentFilter 中的操作;否则,我们将忽略该过滤器并继续处理链中的下一个过滤器。

    您可以在 web.xml 中配置此过滤器而不是 AmAgentFilter

    【讨论】:

    • 我完全忘记了抽象代理类。我正在调试代码,发现在 index.jsp 中调用的 loginaction 没有进入 dofilter,所以我无法从前端获取用户类型。我正在寻找 servletRequest.getParameter(Constant.USER_TYPE);在 web.xml 中,第一个过滤器是 struts 过滤器,然后是它的 customfilter
    • 无论您如何在 servlet 过滤器中获取用户类型,您都可以在扩展 AmAgentFilter 的过滤器中以相同的方式进行操作。 “在 web.xml 中,第一个过滤器是 struts duiker,然后是它的 customfilter”是一个问题吗?如果是这样,那么是的,我认为这会奏效。但是,我不熟悉 struts 过滤器的工作原理。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-06-08
    • 1970-01-01
    • 2018-10-08
    相关资源
    最近更新 更多