static factory method로 빈 생성
스프링으로 전환하기 1:07 부터의 강의 내용에 추가로 공부하다가 생긴 의문점에 관한 내용입니다.
스프링공식문서
위의 공식문서에서는 빈을 생성하는 또다른 방법으로 정적 팩터리 메서드가 있다고 했습니다.
public class StaticFactoryMethodBean {
private String value;
private StaticFactoryMethodBean(String value) {
this.value = value;
}
public static StaticFactoryMethodBean createInstance(String value) {
return new StaticFactoryMethodBean(value);
}
}이런 클래스가 있다고 가정하면, 두가지 종류의 빈을 만들 수 있습니다.
@Configuration
public class AppConfig {
@Bean
public StaticFactoryMethodBean factoryMethodBean() {
return StaticFactoryMethodBean.createInstance("value");
}
@Bean
public static StaticFactoryMethodBean staticFactoryMethodBean() {
return StaticFactoryMethodBean.createInstance("value");
}
}
여기서 생기는 궁금점이 있어서 질문드립니다.
이 static 빈은 @Configuration 에 영향을 받지 않고, 프록시를 생성하지 않아 여러 기능들을 쓸 수 없다고 생각이 들었습니다.
그럼에도 이걸 쓰는 경우가 있을까 해서 질문드립니다. 제 생각엔 외부 라이브러리나 이런거를 쓸 때, 쓸 거 같기도 하단 생각이 들었습니다. 혹시 실무에서도 쓰는 경우가 종종 있었는지 여쭈어봅니다.
p.s 실제 두개 다 생성이 되는지에 대한 검증 테스트 완료(간단하게 main테스트로 진행)
public class StaticFactoryMethodBeanMain {
public static void main(String[] args) {
ApplicationContext context = new AnnotationConfigApplicationContext(AppConfig.class);
StaticFactoryMethodBean factoryMethodBean = context.getBean("factoryMethodBean", StaticFactoryMethodBean.class);
System.out.println(factoryMethodBean);
StaticFactoryMethodBean staticFactoryMethodBean = context.getBean("staticFactoryMethodBean", StaticFactoryMethodBean.class);
System.out.println(staticFactoryMethodBean);
}
}
답변 2
2
안녕하세요. 임형준님
static을 사용하면 다른 빈들보다 더 빠르게 빈을 조기에 로딩할 수 있습니다.
참고로 이 방법은 일반적인 경우에는 사용하지 않습니다.
예를 들어서 빈 포스트 프로세서 같은 곳에서는 모든 빈을 체크해야 하는데, 그 전에 빈이 필요하다면 static을 사용해서 다른 빈 보다 빈을 초기에 등록할 수 있습니다.
이 부분은 빈 포스트 프로세서 같은 것을 공부해보시면 이해하는데 도움이 되실거에요.
빈 포스트 프로세서는 스프링 핵심원리 고급편에서 다룹니다.
감사합니다.
0
안녕하세요. 임형준님, 공식 서포터즈 David입니다.
답변 드리는데 필요한 정보를 요청드립니다:)
이 static 빈은
@Configuration에 영향을 받지 않고, 프록시를 생성하지 않아
이 부분에 대해서 조금 더 자세히 설명 부탁드립니다.
static 빈이 @Configuration에 영향을 받지 않는 이유
(무엇에 대한) 프록시를 생성하지 않는 이유
제 생각엔 외부 라이브러리나 이런거를 쓸 때, 쓸 거 같기도 하단 생각이 들었습니다.
형준님께서 생각하신 외부 라이브러이에서의 사용 예시를 들어주실 수 있으실까요?
감사합니다.
0
<1, 2번에 대한 저의 설명>
https://docs.spring.io/spring-framework/reference/core/beans/java/basic-concepts.html
> When @Bean methods are declared within classes that are not annotated with @Configuration - or when @Configuration(proxyBeanMethods=false) is declared -, they are referred to as being processed in a "lite" mode. In such scenarios, @Bean methods are effectively a general-purpose factory method mechanism without special runtime processing (that is, without generating a CGLIB subclass for it).
@Bean 메서드가 @Configuration으로 애노테이션이 지정되지 않은 클래스 내부에서 선언되거나, @Configuration(proxyBeanMethods=false)가 선언된 경우, 이를 "라이트" 모드에서 처리된다. 이러한 시나리오에서 @Bean 메서드는 사실상 특별한 런타임 처리 없이 범용 목적의 팩토리 메서드 메커니즘으로 동작한다.
> As a consequence, @Bean methods on classes without runtime proxying are not meant to declare inter-bean dependencies at all. Instead, they are expected to operate on their containing component’s fields and, optionally, on arguments that a factory method may declare in order to receive autowired collaborators.
그 결과, 런타임 프록시가 없는 클래스의 @Bean 메서드는 빈 간의 의존성을 선언하기 위한 용도로 사용되지 않는다. 대신, 이러한 메서드는 해당 컴포넌트의 필드에 대해 동작하고, 선택적으로 팩토리 메서드가 자동 주입된 협력자를 받기 위해 선언할 수 있는 인자에 대해 동작하는 것으로 예상된다.
즉, @Configuration이 적용된 클래스는 스프링 컨테이너에 의해서 CGLIB 프록시로 감싸집니다. static 메서드는 인스턴스가 아니기 때문에 @Configuration의 적용을 받지 않습니다.
<외부 라이브러이에서의 사용 예시>
그냥 이 부분은 생각만 하고 검증한 것은 아니라 틀릴 수도 있습니다. 죄송합니다.
그냥 단순히 레디스 같은 외부라이브러리의 환경셋팅을 변경해서 적용하거나 할 때, 쓰일 수 있을거 같다는 저의 생각이었습니다.
구현체가 동적으로 정해질 때, 팩토리 기법을 사용하나요?
0
47
2
MemberService의 인터페이스를 왜 사용하는지 궁금합니다.
0
72
1
롬복 @Setter를 써야 하는 상황이 있는건가요?
0
87
1
빈 등록 메서드의 파라미터가 빈이 아니어도 되나요?
0
79
1
테스트 속도가 나중에 영향이 있을까요?
0
75
1
gradle 설정 안떠서 질문 남깁니다!
0
116
2
build.gradle로 프로젝트를 여는 이유
0
81
1
provider 사용하는 이유
0
85
1
다음 강의 뭘 들어야 할까요
0
123
2
프로토타입 빈, 직접 destroy 호출 안 할 경우
0
62
1
beanB
0
79
2
퀴즈다시풀기
0
63
1
Gradle로 바꿔도 오류가 똑같이 발생하네요 ㅠㅠ
0
90
2
"중복 등록과 충돌" 강의에서 강사님과 다른 에러가 발생합니다.
0
63
3
run 실행했는데 결과창이 이렇게 뜨네요 왜 그런건가요>
0
102
2
도메인의 정의?
0
57
1
ApplicationContext 질문입니다.
0
60
1
@Scope의 proxyMode를 사용할때 단위 테스트 방법
0
86
2
ai api 선정하기 관련 질문
0
115
2
생성자 자동주입 관련해서
0
60
1
생성자 직접 호출 vs 팩토리 메서드 패턴
0
93
2
Spring에서 SessionScope와 RequestScope는 함께 사용되나요?
1
63
1
12:25
0
74
2
appConfig.xml 오류
0
125
1





