source

스프링 부트 2.1 bean 오버라이드 vs기본적인

nicesource 2023. 3. 10. 22:06
반응형

스프링 부트 2.1 bean 오버라이드 vs기본적인

Spring Boot 2.1에서는 콩 오버라이드는 디폴트로 디세블로 되어 있습니다.이것은 좋은 일입니다.

하지만 Mockito를 사용하여 콩을 조롱된 인스턴스로 교체하는 테스트를 몇 가지 했습니다.디폴트 설정에서는 Tests with this configuration은 bean override로 인해 실패합니다.

응용 프로그램 속성에서 bean override를 활성화하는 방법밖에 없었습니다.

spring.main.allow-bean-definition-overriding=true

단, 테스트 구성에 대해 최소한의 bean definition 설정을 확인하고 싶습니다.이 설정은 오버라이드가 무효가 되어 있는 봄까지 지적될 것입니다.

제가 우선하는 콩은

  • 테스트 구성으로 Import한 다른 구성에 정의되어 있습니다.
  • 주석 검색을 통해 자동으로 검색된 콩

테스트 구성에서는 bean을 오버라이드하고 slap으로 동작해야 합니다.@Primary데이터 소스 구성에 익숙해져 있는 것처럼, 그 위에 있습니다.그러나 이것은 효과가 없고, 나는 다음과 같은 의문을 갖게 한다.이요?@Primary장애인이라는 게 모순인가요?

몇 가지 예:

package com.stackoverflow.foo;
@Service
public class AService {
}

package com.stackoverflow.foo;
public class BService {
}

package com.stackoverflow.foo;
@Configuration
public BaseConfiguration {
    @Bean
    @Lazy
    public BService bService() {
        return new BService();
    }
}

package com.stackoverflow.bar;
@Configuration
@Import({BaseConfiguration.class})
public class TestConfiguration {
    @Bean
    public BService bService() {
        return Mockito.mock(BService.class);
    }
}

spring.main.allow-bean-definition-overriding=true는 테스트 구성에 배치할 수 있습니다.광범위한 통합 테스트가 필요한 경우 어느 시점에서 콩을 덮어쓸 필요가 있습니다.어쩔 수 없어요.

정답은 이미 나왔지만 콩의 이름이 다를 수 있다는 뜻이다.그러니까 엄밀히 말하면 오버라이드가 아니라

실제 오버라이드가 필요한 경우(사용자가@Qualifiers,@ResourcesSpring Boot 2.X는 를 사용해야만 가능하기 때문에spring.main.allow-bean-definition-overriding=true소유물.

업데이트: Kotlin Bean Definition DSL에 주의하십시오.스프링 부트에서는 다음과 같은 커스텀 Application Context Initializer가 필요합니다.

class BeansInitializer : ApplicationContextInitializer<GenericApplicationContext> {

    override fun initialize(context: GenericApplicationContext) =
            beans.initialize(context)

}

테스트에서 DSL 기반 콩 중 하나를 덮어쓰기로 결정한 경우@Primary @Bean방법으로는 안 됩니다.이니셜라이저는 다음 시간 후에 시작됩니다.@Bean테스트에서 DSL 기반의 초기 빈을 얻을 수 있습니다.@Primary시험 중에@Bean또 하나의 옵션은 테스트용 이니셜라이저를 생성하여 테스트 속성에 모두 표시하는 것입니다(순서 중요).

context:
    initializer:
        classes: com.yuranos.BeansInitializer, com.yuranos.TestBeansInitializer

Bean Definition DSL은 다음을 통해 프라이머리 속성도 지원합니다.

bean(isPrimary=true) {...}

- 콩을 주입할 때는 애매함을 없애야 하지만, 순수 DSL 방식으로는 필요하지 않습니다.

(스프링 부트 2.1.3)

콩을 덮어쓰는 것은 컨텍스트에서 고유한 이름 또는 ID를 가진 콩이 하나만 있을 수 있음을 의미합니다.따라서 다음과 같은 방법으로 두 개의 콩을 제공할 수 있습니다.

package com.stackoverflow.foo;
@Configuration
public class BaseConfiguration {
   @Bean
   @Lazy
   public BService bService1() {
       return new BService();
   }
}

package com.stackoverflow.bar;
@Configuration
@Import({BaseConfiguration.class})
public class TestConfiguration {
    @Bean
    public BService bService2() {
        return Mockito.mock(BService.class);
    }
}

@Primary디폴트로는 프라이머리 빈이 다음 위치에 주입됩니다.

@Autowired
BService bService;

테스트용 콩은 다음에서만 구할 수 있습니다.test다음과 같이 테스트 중에만 덮어쓸 수 있습니다.

@ActiveProfiles("test")
@SpringBootTest(properties = {"spring.main.allow-bean-definition-overriding=true"})
class FooBarApplicationTests {

  @Test
  void contextLoads() {}
}

테스트 설정에서 조롱하고 있는 콩:

@Profile("test")
@Configuration
public class FooBarApplicationTestConfiguration {
  @Bean
  @Primary
  public SomeBean someBean() {
    return Mockito.mock(SomeBean.class);
  }
}

기본적으로는 @Component를 @Bean으로 덮어쓸 수 있습니다.고객님의 경우

@Service
public class AService {
}

@Component
public class BService {
    @Autowired
    public BService() { ... }
}

@Configuration
@ComponentScan
public BaseConfiguration {
}

@Configuration
// WARNING! Doesn't work with @SpringBootTest annotation
@Import({BaseConfiguration.class})
public class TestConfiguration {
    @Bean // you allowed to override @Component with @Bean.
    public BService bService() {
        return Mockito.mock(BService.class);
    }
}

언급URL : https://stackoverflow.com/questions/53139244/spring-boot-2-1-bean-override-vs-primary

반응형