복붙노트

[SPRING] HttpSessionListener 구현 내부의 Dependency Injection

SPRING

HttpSessionListener 구현 내부의 Dependency Injection

문제 :이 주입 된 의존성은 항상 SimpleController에서 0을 반환합니다.

Github webApp 프로젝트 소스에 대한 프로젝트

다음을 고려하세요:

SessionCounterListener

public class SessionCounterListener implements HttpSessionListener {

  @Autowired
  private SessionService sessionService;

  @Override
  public void sessionCreated(HttpSessionEvent arg0) {
    sessionService.addOne();
  }

  @Override
  public void sessionDestroyed(HttpSessionEvent arg0) {
    sessionService.removeOne();
  } 
}

을 포함한다.

<web-app ...>
    <listener>
        <listener-class>com.stuff.morestuff.SessionCounterListener</listener-class>
    </listener>

</web-app>

applicationContext.xml

<xml ...>

   <!-- Scan for my SessionService & assume it has been setup correctly by spring-->
   <context:component-scan base-package="com.stuff"/>

</beans>

서비스 : SessionService

@Service
public class SessionService{

  private int counter = 0;

  public SessionService(){}

  public void addOne(){
    coutner++;
  }

  public void removeOne(){
    counter--;
  }

  public int getTotalSessions(){
     return counter;
  }

}

컨트롤러 : SimpleController

@Component
public SimpleController
{
  @Autowired
  private SessionService sessionService;

  @RequestMapping(value="/webAppStatus")
  @ResponseBody
  public String getWebAppStatus()
  {
     return "Number of sessions: "+sessionService.getTotalSessions();
  }

}

해결법

  1. ==============================

    1.web.xml에서 를 그렇게 선언하면

    web.xml에서 를 그렇게 선언하면

    <listener>
        <listener-class>com.stuff.morestuff.SessionCounterListener</listener-class>
    </listener>
    

    당신은 서블릿 컨테이너에게 listener-class 요소에 명시된 클래스를 인스턴스화하라고 말하고있다. 즉,이 인스턴스는 Spring에 의해 관리되지 않으므로 아무것도 삽입 할 수 없으며 필드는 null로 남습니다.

    이에 대한 해결 방법이 있습니다. 그리고 좀 더.

    이 점에 유의하십시오.

    <!-- Scan for my SessionService & assume it has been setup correctly by spring-->
    <context:component-scan base-package="com.stuff"/>
    

    web.xml의 유효한 항목이 아닙니다. 나는 그것이 당신의 부분에 복사 실수인지 여부를 모르겠습니다.

  2. ==============================

    2.이것은 실제 솔루션을 보여주는 대답입니다.

    이것은 실제 솔루션을 보여주는 대답입니다.

    SessionCountListener를 다음과 같이 수정해야합니다. 위의 예제가 작동합니다.

    public class SessionCounterListener implements HttpSessionListener {
    
      @Autowired
      private SessionService sessionService;
    
      @Override
      public void sessionCreated(HttpSessionEvent arg0) {
        getSessionService(se).addOne();
      }
    
      @Override
      public void sessionDestroyed(HttpSessionEvent arg0) {
        getSessionService(se).removeOne();
      }
    
      private SessionService getSessionService(HttpSessionEvent se) {
        WebApplicationContext context = 
          WebApplicationContextUtils.getWebApplicationContext(
            se.getSession().getServletContext());
        return (SessionService) context.getBean("sessionService");
      } 
    }
    
  3. from https://stackoverflow.com/questions/20476760/dependency-injection-inside-of-httpsessionlistener-implementation by cc-by-sa and MIT license