Question Utiliser des haricots dans la classe Filter bean?


Dans ma classe de bean filter, j'ai ajouté quelques dépendances de beans (avec @Autowired annotation). Mais dans la méthode doFilter(), tous mes beans de dépendance ont 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 est égal à null (et autres beans dépendants à) ...

Pourriez-vous m'aider ?


En fait, je n'utilise pas la notion de MVC côté serveur (Spring). Pour mon client, j'utilise la technologie Flex et le servlet BlazeDS communique avec mon serveur.

C'est la raison pour laquelle j'utilise la notion de filtre bean.

Alors, comment puis-je gérer la notion de bean de session dans mon bean Filter?


Skaffman,

J'ai implémenté votre idée, alors je mets à jour mon application.xml avec:

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

et mon FacebookOuthHandler classe:

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

Mais cette méthode handleRequestInternal n'est jamais appelé lorsque mon URL est: http: //xx.xx.xx.xx/MyApp/fbauth


15
2017-09-05 09:51


origine


Réponses:


J'étais confronté au même problème et ma première idée était de forcer manuellement Spring à appliquer l'annotation @Autowired au filtre comme proposé ici

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

Mais je n'aime pas l'idée de coder en dur le nom du bean dans ma classe Java.

J'ai trouvé un moyen plus propre qui fonctionne aussi bien:

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

28
2017-08-13 15:59



En supposant cela Filter est branché dans votre web.xml, alors cela ne fonctionnera pas, car il n'est pas géré par Spring, il est géré par le conteneur de servlets. Donc, des choses comme le démarrage automatique ne fonctionneront pas.

Si vous voulez définir un filtre de servlet en tant que bean Spring, vous devez le définir dans le contexte d’application racine de l’application Web (en utilisant un ContextLoaderListener dans web.xml), puis définir un DelegatingFilterProxy qui délègue à votre haricot géré par le printemps pour faire le travail.

Cependant, avez-vous vraiment besoin d'un filtre de servlet pour cela? Qu'est-ce que je sais de choses d'authentification Facebook, cela pourrait être fait aussi facilement avec un ressort HandlerInterceptor. Ce serait beaucoup moins de travail de configuration qu'un filtre de délégation.


13
2017-09-05 10:13



Regardez cette réponse sur le site du printemps: http://forum.springsource.org/showthread.php?60983-Autowiring-the-servlet-filter

En bref - vous pouvez forcer manuellement Spring à appliquer l'annotation @Autowire à votre filtre:

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

7
2017-08-28 15:24



Je le sais maintenant une vieille question, mais il n'y a pas d'exemple d'utilisation de DelegatingFilterProxy dans les réponses actuelles, et une question récente demandant un tel exemple a été marquée en double pour celui-ci.

Donc un DelegatingFilterProxy est un filtre spécial qui connaît la racine ApplicationContext et délègue son doFilterà un haricot.

Exemple : MyFilter est une classe implémentant Filter, et myFilter est une fève de printemps

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

ou dans une classe de configuration

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

Dans web.xml, vous déclarez simplement un DelegatingFilterProxy avec le même nom que le haricot:

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

De cette façon, comme myBean est un vrai haricot, il peut être injecté normalement avec d'autres haricots avec @Autowired annotations et ses doFilter la méthode sera appelée par le DelegatingFilterProxy. Comme vous pouvez utiliser les méthodes spring init et destroy, par défaut init et destroy les méthodes ne seront pas appelées, à moins que vous ne spécifiiez le filtre "targetFilterLifecycle" init-param comme "true".


7
2017-10-02 16:21



J'obtenais un pointeur null lors de l'accès à la classe de service bean dans la classe de filtre à l'aide de Autowiring. J'ai cherché plus de 100 liens mais je n'ai pas pu trouver de solution. J'utilise l'application Spring Boot et la configuration requise pour obtenir le bean dans la classe de filtre:

FilterConfig.java qui fournit l'objet Contexte d'application.

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

 }

dans la classe Filter, j'ai utilisé ceci comme:

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

UserService c'est le nom du bean qui est mentionné dans

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

Aucune configuration dans la classe principale du printemps Boot: SpringBootServletInitializer


1
2017-10-22 14:16