为什么Filter类没有解决所需的依赖关系?

时间:2017-08-23 10:07:26

标签: spring spring-boot dependency-injection servlet-filters spring-filter

我正在使用Spring Boot Filters,并且要求在我的Filter中使用我的一个服务。

以下是我正在使用的代码:

    @WebFilter(urlPatterns = {"/getDocs" })
public class AuthenticationFilter implements Filter{

    private static Logger logger = Logger.getLogger(AuthenticationFilter.class);

    @Autowired
    private UserVerificationService userVerificationService;

    @Override
    public void destroy() {
        // TODO Auto-generated method stub

    }

    @Override
    public void doFilter(ServletRequest arg0, ServletResponse response, FilterChain chain)
            throws IOException, ServletException {

        logger.info("checking token in filter");
        HttpServletRequest request = (HttpServletRequest) arg0;

        DocVerificationRequestWrapper myRequestWrapper = new DocVerificationRequestWrapper((HttpServletRequest) request);

        String body = myRequestWrapper.getBody();
        logger.info("body = "+body);
        Token token = null;
        try {
            JSONObject jsonObj = new JSONObject(body);
            JSONObject tokenObj = (JSONObject) jsonObj.get("token");
            Gson gson = new Gson();
            token = gson.fromJson(tokenObj.toString(), Token.class);

            logger.info("Got Token Object = "+token);
            logger.info("   Token  = "+token.get_id());
            logger.info("   Token Access Token = "+token.getAccessToken());
            logger.info("   Token Role Id = "+token.getRoleId());

            if(null != token) {

                    String verStatus = userVerificationService.verifyUser(token);
                    logger.info("verStatus = "+verStatus);
                    if(verStatus != null && verStatus.equalsIgnoreCase("success"))
                        chain.doFilter(request, response);
                    else
                        logger.error("Invalid token");
            }else {
                    logger.error("token missing.");
            }
        } catch (JSONException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }

    @Override
    public void init(FilterConfig arg0) throws ServletException {
        // TODO Auto-generated method stub

    }

}

我解析了RequestWrapper返回的正文并将其转换为令牌对象。但是当从UserVerificationService类调用verifyUser方法时,我得到了空指针异常,它声明UserVerificationService bean没有初始化。

这是我得到的异常堆栈跟踪:

    15:31:38.017 [http-nio-8080-exec-3] INFO  c.c.d.filters.AuthenticationFilter - Got Token Object = com.ct.docverification.model.Token@5fc79544
 15:31:38.017 [http-nio-8080-exec-3] INFO  c.c.d.filters.AuthenticationFilter -     Token  = null
 15:31:38.017 [http-nio-8080-exec-3] INFO  c.c.d.filters.AuthenticationFilter -     Token Access Token = f2830dee-7f5d-44c5-ac7b-e7a32f8baa9f
 15:31:38.017 [http-nio-8080-exec-3] INFO  c.c.d.filters.AuthenticationFilter -     Token Role Id = [1.0]
 15:31:38.022 [http-nio-8080-exec-3] ERROR o.s.boot.web.support.ErrorPageFilter - Forwarding to error page from request [/getDocs] due to exception [null]
java.lang.NullPointerException: null
    at com.ct.docverification.filters.AuthenticationFilter.doFilter(AuthenticationFilter.java:68)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.web.filter.RequestContextFilter.doFilterInternal(RequestContextFilter.java:99)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.web.filter.HttpPutFormContentFilter.doFilterInternal(HttpPutFormContentFilter.java:105)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.web.filter.HiddenHttpMethodFilter.doFilterInternal(HiddenHttpMethodFilter.java:81)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:197)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.springframework.boot.web.support.ErrorPageFilter.doFilter(ErrorPageFilter.java:115)
    at org.springframework.boot.web.support.ErrorPageFilter.access$000(ErrorPageFilter.java:59)
    at org.springframework.boot.web.support.ErrorPageFilter$1.doFilterInternal(ErrorPageFilter.java:90)
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107)
    at org.springframework.boot.web.support.ErrorPageFilter.doFilter(ErrorPageFilter.java:108)
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:198)
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:96)
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:478)
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:140)
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:80)
    at org.apache.catalina.valves.AbstractAccessLogValve.invoke(AbstractAccessLogValve.java:624)
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:87)
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:342)
    at org.apache.coyote.http11.Http11Processor.service(Http11Processor.java:799)
    at org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:66)
    at org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:868)
    at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1455)
    at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:49)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
    at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
    at java.lang.Thread.run(Thread.java:745)

我是否需要在弹簧启动配置中单独注册过滤器?或任何建议,如何解决这个问题?

1 个答案:

答案 0 :(得分:0)

我通过使用webapplicationcontext和servletContext懒惰初始化userService解决了这个问题,如下所示:

public void doFilter(ServletRequest arg0, ServletResponse response, FilterChain chain)
        throws IOException, ServletException {

    logger.info("checking token in filter");
    HttpServletRequest request = (HttpServletRequest) arg0;
    DocVerificationRequestWrapper myRequestWrapper = new DocVerificationRequestWrapper((HttpServletRequest) request);
    String body = myRequestWrapper.getBody();
    Token token = null;
    try {
        JSONObject jsonObj = new JSONObject(body);
        JSONObject tokenObj = (JSONObject) jsonObj.get("token");
        Gson gson = new Gson();
        token = gson.fromJson(tokenObj.toString(), Token.class);

        if(null != token) {
                //here initialising the userVerificationService
                if(userVerificationService==null){
                ServletContext servletContext = request.getServletContext();
                WebApplicationContext webApplicationContext = WebApplicationContextUtils.getWebApplicationContext(servletContext);
                userVerificationService = webApplicationContext.getBean(UserVerificationService.class);
            }
                String verStatus = userVerificationService.verifyUser(token);
                logger.info("verStatus = "+verStatus);
                if(verStatus != null && verStatus.equalsIgnoreCase("success")) {
                    chain.doFilter(request, response);  
                }else
                    logger.error("Invalid token");
        }else {
                logger.error("token missing.");
        }
    } catch (JSONException e) {
            logger.error("exception in authetication filter " + e);
    }
}