Подтвердить что ты не робот

Использование некоторого beans в классе Filter bean?

В моем классе bean я добавил некоторую зависимость beans (с аннотацией @Autowired). Но в методе doFilter() вся моя зависимость beans имеет значение 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.oAuthHelper равен нулю (и другой зависимости beans to)...

Не могли бы вы мне помочь?


На самом деле я не использую понятие MVC на стороне сервера (Spring). Для моего стороннего клиента я использую технологию Flex, а сервлет SLazeDS связывается с моим сервером.

Итак, вот почему я использую понятие Filter bean.

Итак, как я могу обрабатывать свой сеанс bean в моем фильтре bean?


Skaffman,

Я реализовал вашу идею, поэтому я обновляю свой 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>

и класс 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;
}

Но этот метод handleRequestInternal никогда не вызывается, когда мой URL-адрес: http://xx.xx.xx.xx/MyApp/fbauth

4b9b3361

Ответ 1

Я столкнулся с одной и той же проблемой, и моя первая идея заключалась в том, чтобы вручную заставить Spring применять @Autowired аннотацию к фильтру, как предлагается здесь

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

Но мне не нравится идея жесткого кодирования имени bean в моем классе Java.

Я нашел более чистый способ, который работает также:

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

Ответ 2

Предполагая, что этот Filter подключен к вашему web.xml, это не сработает, так как он не управляется Spring, он управляется контейнером сервлета. Поэтому такие вещи, как автоустановка, не будут работать.

Если вы хотите определить фильтр сервлета как Spring bean, вам нужно определить его в контексте корневого приложения webapp (используя ContextLoaderListener в web.xml), а затем определяет DelegatingFilterProxy, который делегирует ваш Spring -установленный bean для выполнения этой работы.

Однако для этого вам нужен сервлет-фильтр? Что я знаю об аутсайдерах Facebook, это может быть сделано так же легко с Spring HandlerInterceptor. Это будет значительно меньше работы по настройке, чем делегирующий фильтр.

Ответ 3

Посмотрите на этот ответ на сайте spring: http://forum.springsource.org/showthread.php?60983-Autowiring-the-servlet-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);
}

Ответ 4

Я знаю, что это старый вопрос, но в текущих ответах нет примера использования DelegatingFilterProxy, а один последний вопрос, задающий такой пример, был помечен как дубликат для этого.

Итак, DelegatingFilterProxy - это специальный фильтр, который знает о root ApplicationContext и передает его doFilter в bean.

Пример: MyFilter - это реализация класса Filter, а myFilter - это spring bean

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

или в классе конфигурации

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

В 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>

Таким образом, поскольку myBean является истинным bean, его можно вставлять обычно с помощью других beans с аннотациями @Autowired, а его метод doFilter вызывается DelegatingFilterProxy. Поскольку вы можете использовать методы spring init и destroy, по умолчанию методы init и destroy не будут вызываться, если вы не укажете init-param фильтра targetFilterLifecycle как "true".

Ответ 5

Я получал нулевой указатель при доступе к классу сервиса bean в классе фильтра с использованием Autowiring. Я искал более 100 ссылок, но не смог найти решение. Я использую spring Загрузочное приложение и конфигурацию, необходимые для получения bean в классе фильтра:

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;
}   

 }

в классе Filter, я использовал это как:

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

UserService это bean имя, указанное в

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

Нет конфигурации в основном классе spring Загрузка: SpringBootServletInitializer