Java 在 Filter bean 类中使用一些 bean?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/3645650/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-14 03:06:49  来源:igfitidea点击:

Using some beans in Filter bean class?

javaspringservletsservlet-filters

提问by Anthony

In my filter bean class, I added some beans dependency (with @Autowiredannotation). But in the method doFilter(), all my dependency beans have null ...

在我的过滤器 bean 类中,我添加了一些 bean 依赖项(带@Autowired注释)。但是在该方法中doFilter(),我所有的依赖 bean 都为 null ...

public class FacebookOAuth implements Filter
{
@Autowired
private BusinessLogger logger;

@Autowired
private IUserSessionInfo userSessionInfo;

@Autowired
private FacebookOAuthHelper oAuthHelper;

public void init(FilterConfig fc) throws ServletException
{
    // Nothing to do
}

public void doFilter(ServletRequest sr, ServletResponse sr1, FilterChain fc) throws   IOException, ServletException
{
    // HttpServletRequest req = (HttpServletRequest)sr;
    HttpServletResponse res = (HttpServletResponse) sr1;

    String code = sr.getParameter("code");

    if (StringUtil.isNotBlankStr(code))
    {
        String authURL = this.oAuthHelper.getAuthURL(code);

this.oAuthHelperis equal at null (and other dependancy beans to) ...

this.oAuthHelper等于 null(和其他依赖 bean)...

Could you help me ?

你可以帮帮我吗 ?



In fact I don't use MVC notion on server side (Spring). For my side client I use Flex technology and BlazeDS servlet ton communicate with my server.

事实上,我不在服务器端(Spring)使用 MVC 概念。对于我的侧客户端,我使用 Flex 技术和 BlazeDS servlet 与我的服务器进行通信。

So, that is the reason, I use the Filter bean notion.

所以,这就是我使用 Filter bean 概念的原因。

So, how can I handle my session bean notion in my Filter bean ?

那么,如何在我的 Filter bean 中处理我的会话 bean 概念?



Skaffman,

斯卡夫曼,

I implemented your idea, so I update my application.xml with :

我实现了你的想法,所以我更新了我的 application.xml :

<bean id="FacebookOAuthHandler" class="com.xx.FacebookOAuthHandler" />
<bean class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
    <property name="mappings">
    <props>
       <prop key="/fbauth">FacebookOAuthHandler</prop>         
    </props>
   </property>
</bean>

and my FacebookOAuthHandlerclass :

和我的FacebookOAuthHandler类:

public class FacebookOAuthHandler extends AbstractController
{
@Autowired
private BusinessLogger logger;

@Autowired
private IUserSessionInfo userSessionInfo;

@Autowired
private FacebookOAuthHelper oAuthHelper;

@Override
protected ModelAndView handleRequestInternal(HttpServletRequest request,
        HttpServletResponse response) throws Exception {

    // TODO

    return null;
}

But, this method handleRequestInternalis never called when my URL is : http://xx.xx.xx.xx/MyApp/fbauth

但是,当我的 URL 是:http://xx.xx.xx.xx/MyApp/fbauth时,永远不会调用此方法handleRequestInternal

回答by skaffman

Assuming this Filteris wired up in your web.xml, then this isn't going to work, since it's not managed by Spring, it's managed by the servlet container. So things like autowiring won't work.

假设这Filter是在您的 中连接的web.xml,那么这将不起作用,因为它不是由 Spring 管理的,而是由 servlet 容器管理的。所以像自动装配这样的东西是行不通的。

If you want to define a servlet filter as Spring bean, then you need to define it in the webapp's root application context (using a ContextLoaderListenerin web.xml), and then defining a DelegatingFilterProxywhich delegates to your Spring-managed bean to do the work.

如果要将servlet 过滤器定义为Spring bean,则需要在webapp 的根应用程序上下文中定义它(使用ContextLoaderListenerweb.xml 中的a),然后定义一个DelegatingFilterProxy委托给Spring 管理的bean 来完成工作的a。

However, do you really need a servlet filter for this? What what I know of Facebook auth stuff, this could be done just as easily with a Spring HandlerInterceptor. This would be considerably less configuration work than a delegating filter.

但是,您真的需要为此使用 servlet 过滤器吗?我对 Facebook 身份验证的了解,这可以用 Spring 轻松完成HandlerInterceptor。这将比委派过滤器少得多的配置工作。

回答by Dewfy

Look at this answer on site of spring: http://forum.springsource.org/showthread.php?60983-Autowiring-the-servlet-filter

在 spring 站点上查看此答案:http: //forum.springsource.org/showthread.php?60983-Autowiring-the-servlet-filter

In brief - you can manually force spring to apply @Autowire annotation to your filter:

简而言之 - 您可以手动强制 spring 将 @Autowire 注释应用于您的过滤器:

public void init(FilterConfig filterConfig) throws ServletException {

    ServletContext servletContext = filterConfig.getServletContext();
    WebApplicationContext webApplicationContext = 
            WebApplicationContextUtils.getWebApplicationContext(servletContext);

    AutowireCapableBeanFactory autowireCapableBeanFactory =
           webApplicationContext.getAutowireCapableBeanFactory();

    autowireCapableBeanFactory.configureBean(this, BEAN_NAME);
}

回答by Serge Ballesta

I know it a now old question, but there is no example of usage of DelegatingFilterProxyin current responses, and one recent question asking for such an example was marked as a duplicate for this one.

我知道这是一个现在很老的问题,但是DelegatingFilterProxy在当前的回答中没有使用的示例,最近一个要求这样示例的问题被标记为该示例的重复。

So a DelegatingFilterProxyis a special filter that knows about root ApplicationContextand delegates its doFilterto a bean.

所以 aDelegatingFilterProxy是一个特殊的过滤器,它知道 rootApplicationContext并将其委托doFilter给一个 bean。

Example : MyFilteris a class implementing Filter, and myFilter is a spring bean

示例:MyFilter是一个实现类Filter,而 myFilter 是一个 spring bean

<bean id=myFilter class="org.example.MyFilter ...>...</bean>

or in a configuration class

或在配置类中

@Bean
public MyFilter myFilter() {
    MyFilter myFilter = new MyFilter();
    //initialization ...
    return myFilter;
}

In web.xml, you just declare a DelegatingFilterProxywith same name as the bean :

在 web.xml 中,您只需声明一个DelegatingFilterProxy与 bean 同名的名称:

<filter>
    <filter-name>myFilter</filter-name>
    <filter-class>org.springframework.web.filter.DelegatingFilterProxy</filter-class>
</filter>
<filter-mapping>
    <filter-name>myFilter</filter-name>
    <url-pattern>/*</url-pattern>
</filter-mapping>

That way, as myBeanis a true bean, it can be injected normally with other beans with @Autowiredannotations, and its doFiltermethod will be called by the DelegatingFilterProxy. As you can use spring init and destroy methods, by default initand destroymethods will not be called, unless you specify the "targetFilterLifecycle" filter init-param as "true".

这样,作为myBean一个真正的bean,它可以与其他带@Autowired注解的bean一起正常注入,它的doFilter方法将被DelegatingFilterProxy. 由于您可以使用 spring init 和 destroy 方法,默认情况下不会调用initdestroy方法,除非您将“targetFilterLifecycle”过滤器 init-param 指定为“true”。

回答by Mathias G.

I was facing the same problem and my first idea was to manually force Spring to apply @Autowired annotation to the filter like proposed here

我遇到了同样的问题,我的第一个想法是手动强制 Spring 将 @Autowired 注释应用到过滤器,就像这里建议的那样

http://forum.springsource.org/showthread.php?60983-Autowiring-the-servlet-filter

http://forum.springsource.org/showthread.php?60983-Autowiring-the-servlet-filter

But I don't like the idea of hardcoding the bean name in my Java class.

但是我不喜欢在我的 Java 类中硬编码 bean 名称的想法。

I found an cleaner way that works as well:

我找到了一种更干净的方法:

public void init(FilterConfig filterConfig) throws ServletException {
    SpringBeanAutowiringSupport.processInjectionBasedOnServletContext(this,
            filterConfig.getServletContext());
}

回答by abhishek ringsia

I was getting null pointer while accessing service class bean in filter class using Autowiring . I searched more than 100 links but not able to find solution. I am using spring Boot Application and configuration which is required to get bean in filter class :

我在使用 Autowiring 访问过滤器类中的服务类 bean 时得到空指针。我搜索了 100 多个链接,但找不到解决方案。我正在使用 spring Boot Application 和配置,这是在过滤器类中获取 bean 所需的:

FilterConfig.java which provides application context Object.

FilterConfig.java 提供应用程序上下文对象。

@Component
public class FilterConfig  implements ApplicationContextAware{

private static ApplicationContext context;


public static ApplicationContext getApplicationContext() {
       return context;
    }
public  static <T> T getBean(String name,Class<T> aClass){
    return context.getBean(name,aClass);
}

@Override
public void setApplicationContext(ApplicationContext ctx) throws BeansException {
    context = ctx;
}   

 }

in Filter class , I used this like :

在过滤器类中,我使用了这个:

 UserService userService =FilterConfig.getBean("UserService", UserService.class);

UserService this is bean name which is mentioned in

UserService 这是在中提到的 bean 名称

  @Service("UserService")
  public class UserServiceImpl implements UserService { ...}

No Configuration in main class of spring Boot :SpringBootServletInitializer

spring Boot 主类中没有配置:SpringBootServletInitializer