복붙노트

[SPRING] 부모 컨텍스트에서 자식 컨텍스트와 스프링 컨텍스트 선언

SPRING

부모 컨텍스트에서 자식 컨텍스트와 스프링 컨텍스트 선언

나는 Spring bean (dao) 객체를 가지고 있는데,이 객체는 다음과 같은 XML을 통해 ServletContext에서 인스턴스화한다.

<bean id="userDao" class="com.company.dao.impl.UserDaoImpl">
    <property name="sessionFactory" ref="sessionFactory" />
</bean>

이 bean은 webapp-servlet.xml 파일 내에서 선언되며 ServletContext 내에서 사용됩니다.

나는 또한 SpringSecurity를 ​​사용하고있다. 이것은 다른 컨텍스트 (SecurityContext)에서 실행된다는 것을 알고 있습니다.

내 응용 프로그램에는 custom authentication 공급자를 인스턴스화하는 webapp-security.xml이 있습니다. 내 보안 컨텍스트에서 사용자 조회를 수행하기 위해 내 응용 프로그램에서 사용되는 내 DAO를 사용하고 싶습니다. 그러나 실행할 때 :

<bean id="userAuthenticationProvider" class="com.company.security.UserAuthenticationProvider">
    <property name="userDao" ref="userDao" />
</bean>

그런 bean "userDao"가 없다는 오류가 발생합니다. bean은 내 보안 컨텍스트 내에서가 아니라 내 다른 컨텍스트에서 선언 된 bean에서 자동으로 자동 실행됩니다. Spring Docs에 따르면, 나는 web.xml에서 두 개의 별도 컨텍스트가 필요하다고 생각한다.

<listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener
    </listener-class>
</listener>

<listener>
    <listener-class>
        org.springframework.security.web.session.HttpSessionEventPublisher
    </listener-class>
</listener>

그래서 내 질문은, 내 Security Context 내에서 내 ServletContext에 살고있는 DAO에 어떻게 접근 할 수 있습니까? 내 dao에 대한 범위 한정자가 있습니까, 아니면 어떻게 든 내 인증 공급자 내에서 런타임에 ServletContext를 얻을 수 있습니까? 참고로이 방법을 인증 공급자 내에서 사용하는 방법입니다.

public class UserAuthenticationProvider extends
    AbstractUserDetailsAuthenticationProvider {

    @Override
protected UserDetails retrieveUser(String userName,
        UsernamePasswordAuthenticationToken authenticationToken)
        throws AuthenticationException {

    // use dao here

이걸 설명해 줘서 고마워.

최신 정보:

조사를 계속하면, 내 daos를 사용하고있는 DispatcherServlet이 하위 컨텍스트이고, 보안 컨텍스트가 어딘가에있는 것으로 보입니다. 따라서 DispatcherServlet의 부모는 부모 컨텍스트에서 볼 수 없습니다. 대답은 어떻게 든 내 콩 선언을 부모 응용 프로그램 컨텍스트로 이동하는 것입니다 생각하지만, 어떻게 해야할지 모르겠다. 여기 내 web.xml입니다.

<context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>WEB-INF/spring-*.xml
    </param-value>
</context-param>

<listener>
    <listener-class>
        org.springframework.security.web.session.HttpSessionEventPublisher
    </listener-class>
</listener>

<listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener
    </listener-class>
</listener>

<filter>
    <filter-name>springSecurityFilterChain</filter-name>
    <filter-class>org.springframework.web.filter.DelegatingFilterProxy
    </filter-class>
</filter>

<filter-mapping>
    <filter-name>springSecurityFilterChain</filter-name>
    <url-pattern>/*</url-pattern>
</filter-mapping>

<servlet>
    <servlet-name>myapp</servlet-name>
    <servlet-class>org.springframework.web.servlet.DispatcherServlet
    </servlet-class>
    <load-on-startup>1</load-on-startup>
    <init-param>
        <param-name>listings</param-name>
        <param-value>true</param-value>
    </init-param>
</servlet>

    ...

나는 모든 DAO 생성을 spring-dao.xml로 옮겼다. spring-security.xml에서 나는 현재 다음을 수행하고있다 :

<import resource="spring-dao.xml" />

daos stil은 DispatcherServlet 컨텍스트에 계속 표시되고 SecurityContext에는 보이지 않습니다.

대답 :

알았어, 알아 냈어. 다음은 유용한 링크입니다.

http://static.springsource.org/spring/docs/3.0.x/spring-framework-reference/html/beans.html#context-create

http://forum.springsource.org/showthread.php?115774-Spring-Security-Custom-UserDetailsService-to-use-User-Service-Dao

http://static.springsource.org/spring-security/site/faq.html#faq-method-security-in-web-context

그래서 문제는 dao가 ApplicationContext (상위 스프링 컨테이너)에 있는지 확인해야한다는 것입니다. 이 문제가 발생했는지 확인하기 위해 web.xml을 다음과 같이 변경했습니다.

<context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>WEB-INF/spring-dao.xml WEB-INF/spring-security.xml
    </param-value>
</context-param>

<listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener
    </listener-class>
</listener>

<listener>
    <listener-class>
        org.springframework.security.web.session.HttpSessionEventPublisher
    </listener-class>
</listener>

<filter>
    <filter-name>springSecurityFilterChain</filter-name>
    <filter-class>org.springframework.web.filter.DelegatingFilterProxy
    </filter-class>
</filter>

<filter-mapping>
    <filter-name>springSecurityFilterChain</filter-name>
    <url-pattern>/*</url-pattern>
</filter-mapping>

<servlet>
    <servlet-name>webapp</servlet-name>
    <servlet-class>org.springframework.web.servlet.DispatcherServlet
    </servlet-class>
    <load-on-startup>1</load-on-startup>
    <init-param>
        <param-name>listings</param-name>
        <param-value>true</param-value>
    </init-param>
</servlet>

나는 이것이 나의 DAO 설정 (그리고 나의 DAO 빈을 만든다)을 시작하고, 나의 보안 설정을 읽을 수있는 첫 번째 컨텍스트 로더가 시작될 것이라고 확신했다. dao 빈이 이런 방법으로 생성 되었기 때문에 더 이상 필요하지 않으므로 security.xml의 이전 "import resource ="spring-dao.xml "문을 제거했습니다.

해당 컨텍스트 매개 변수 구성 바로 다음에 ContextLoaderListener를 만들었습니다. 이것은 DispatcherServlet보다 더 높은 수준의 스프링 컨테이너이기 때문에, 먼저이 설정 파일을 읽는 것은 처음으로 그 설정 파일을 읽는 것이고, 그는 콩을 생성 할 것이라고 생각했습니다. 그러면 모든 하위 컨텍스트가 해당 컨텍스트에 액세스 할 수 있습니다. 이것은 DispatcherServlet이 contextConfigLocation을 읽지조차 못하기 때문에 작동하는 방식이 아닐지 모르지만, 그렇다고하더라도 콩이 이미 선언되었으므로 부모 컨텍스트가 부모 컨텍스트를 소유하고 있다고 생각했습니다.

자, 다른 트릭을 위해서 ... DAO를 얻기 위해서, 나는 그것을 @Autowired 수 없었다. XML을 통해 수동으로 주입해야했습니다.

    <bean id="userAuthenticationProvider" class="com.company.app.security.UserAuthenticationProvider">
    <property name="userDao" ref="userDao" />
</bean>

물론, 나는 나의 dao와 voila 위에서 getter와 setter 방법을 만들었다! @Autowired가 왜 여기에서 작동하지 않는지 나는 모른다. 나는 그것이 설계에 의한 것이라고 가정한다. 아마도 이것은 SecurityContext (다른 컨텍스트에서 가져 오지 않을 것입니다) 또는 아마도 @Autowired는 일반적으로 현재 컨텍스트에서 가져옵니다 또는 내가 XML을 통해 빈을 만들었 기 때문에 xml을 통해 속성을 설정해야합니다. 특수 효과를 통하지 않고? (주석은 활성화되어 있고 최상위 레벨 응용 프로그램 네임 스페이스에서 작동합니다).

어쨌든 .. 아직 많이 이해가 안되지만, 중요한 점은 마침내 효과가 있다는 것입니다.

해결법

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

    1.Spring MVC를 사용한다면 Spring MVC의 ApplicationContext 계층 구조를 이해해야한다. 또한 서블릿 컨테이너의 기본 구성 요소와 수명주기에 대해 알아야합니다. 리스너와 서블릿의 작동 방식에 대해 혼동을 느끼기 때문입니다.

    Spring MVC를 사용한다면 Spring MVC의 ApplicationContext 계층 구조를 이해해야한다. 또한 서블릿 컨테이너의 기본 구성 요소와 수명주기에 대해 알아야합니다. 리스너와 서블릿의 작동 방식에 대해 혼동을 느끼기 때문입니다.

    간략하게 상황을 설명하려면 다음을 수행하십시오.

  2. from https://stackoverflow.com/questions/7746633/declaring-spring-bean-in-parent-context-vs-child-context by cc-by-sa and MIT license