์ปดํฌ๋ํธ ์ค์บ
์ปดํฌ๋ํธ ์ค์บ & ์์กด๊ด๊ณ ์๋์ฃผ์
๋งค๋ฒ @Bean
์ด๋ XML ํ์ผ๋ก ์คํ๋ง ๋น์ ์ง์ ๋ฑ๋กํด์ฃผ๋ฉด ๋งค์ฐ ๋ฒ๊ฑฐ๋ก์
โ ์ปดํฌ๋ํธ ์ค์บ: ์ค์ ์ ๋ณด๊ฐ ์์ด๋ ์๋์ผ๋ก ์คํ๋ง๋น์ ๋ฑ๋กํด์ฃผ๋ ๊ธฐ๋ฅ
โ ์์กด ๊ด๊ณ ์๋ ์ฃผ์
: @Autowired
package hello.core;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.FilterType;
@Configuration
@ComponentScan(
excludeFilters = @ComponentScan.Filter(type = FilterType.ANNOTATION, classes = Configuration.class)
)
public class AutoAppConfig {
}
โ @ComponentScan
์ ์ค์ ์ ๋ณด์ ๋ถ์ฌ์ฃผ๋ฉด @Component
annotation์ด ๋ถ์ ํด๋์ค๋ฅผ ์ค์บํด์ ์คํ๋ง ๋น์ผ๋ก ๋๋กํ๋ค
@Bean
์ผ๋ก ๋ฐ๋ก ํด๋์ค๋ฅผ ๋ฑ๋กํ์ง ์์๋ ๋๋ค
// MemoryMemberRepository.java
@Component
public class MemoryMemberRepository implements MemberRepository {}
// RateDiscountPolicy.java
@Component
public class RateDiscountPolicy implements DiscountPolicy {}
// MemberServiceImpl.java
@Component
public class MemberServiceImpl implements MemberService {
private final MemberRepository memberRepository;
@Autowired
public MemberServiceImpl(MemberRepository memberRepository) {
this.memberRepository = memberRepository;
}
}
@Component
public class OrderServiceImpl implements OrderService {
private final MemberRepository memberRepository;
private final DiscountPolicy discountPolicy;
@Autowired
public OrderServiceImpl (MemberRepository memberRepository, DiscountPolicy discountPolicy) {
this.memberRepository = memberRepository;
this.discountPolicy = discountPolicy;
}
}
์ค์ ์ ๋ณด(์ด์ ์ Appconfig)์ด ๋ฐ๋ก ์๊ธฐ ๋๋ฌธ์ ์์กด๊ด๊ณ ์ฃผ์ ๋ ํด๋์ค ์์์ ํด๊ฒฐํด์ผ ํ๋ค
@Autowired
์์กด๊ด๊ณ ์๋ ์ฃผ์
ํ ์คํธ ์ฝ๋
public class AutoAppConfigTest {
@Test
void basicScan() {
AnnotationConfigApplicationContext ac = new AnnotationConfigApplicationContext(AutoAppConfig.class);
MemberService memberService = ac.getBean(MemberService.class);
assertThat(memberService).isInstanceOf(MemberService.class);
}
}
ClassPathBeanDefinitionScanner - Identified candidate component class:
.. RateDiscountPolicy.class
.. MemberServiceImpl.class
.. MemoryMemberRepository.class
.. OrderServiceImpl.class
์ปดํฌ๋ํธ ์ค์บ์ด ์ ๋์ํ๋ค
์ปดํฌ๋ํธ ์ค์บ์ ์๋ฆฌ
1. @ComponentScan

โ @ComponentScan
์ @Component
๊ฐ ๋ถ์ ๋ชจ๋ ํด๋์ค๋ฅผ ์คํ๋ง ๋น์ผ๋ก ๋ฑ๋กํ๋ค.
์คํ๋ง ๋น์ ๊ธฐ๋ณธ ์ด๋ฆ์ ํด๋์ค๋ช ์ ์ฌ์ฉํ๋ ๋งจ ์๊ธ์๋ง ์๋ฌธ์๋ฅผ ์ฌ์ฉํ๋ค.(MemberServiceImpl -> memberServiceImpl )
๋น ์ด๋ฆ ์ง์ ์ง์ : ๋ง์ฝ ์คํ๋ง ๋น์ ์ด๋ฆ์ ์ง์ ์ง์ ํ๊ณ ์ถ์ผ๋ฉด @Component("memberService2")
์ด๋ฐ์์ผ๋ก ์ด๋ฆ์ ๋ถ์ฌํ๋ฉด ๋๋ค.
2. @Autowired
์์กด๊ด๊ณ ์๋ ์ฃผ์

โ ์์ฑ์์ @Autowired ๋ฅผ ์ง์ ํ๋ฉด ์คํ๋ง ์ปจํ ์ด๋๊ฐ ์๋์ผ๋ก ํด๋น ์คํ๋ง ๋น์ ์ฐพ์์ ์ฃผ์
๊ธฐ๋ณธ์ ์ผ๋ก๋ ํ์
์ด ๊ฐ์ ๋น์ ์ฐพ์์ ์ฃผ์
ํ๋ค (getBean(MemberRepository.class)
์ ๋์ผ)
ํ์ ์์น์ ๊ธฐ๋ณธ ์ค์บ๋์
ํ์ํ ํจํค์ง์ ์์ ์์น ์ง์
๋ชจ๋ ์๋ฐ ํด๋์ค๋ฅผ ๋ค ์ค์บํ๋ฉด ์๊ฐ์ด ์ค๋ ๊ฑธ๋ฆผ -> ๊ผญ ํ์ํ ์์น๋ถํฐ ํ์ํ๋๋ก ์์ ์์น ์ง์ ๊ฐ๋ฅ
@ComponentScan(
basePackages = "hello.core",
)
basePackages
: ํ์ํ ํจํค์ง์ ์์ ์์น๋ฅผ ์ง์ ํ๋ค. ์ด ํจํค์ง๋ฅผ ํฌํจํด์ ํ์ ํจํค์ง๋ฅผ ๋ชจ๋ ํ์ํ๋ค.
basePackages = {"hello.core", "hello.service"}
์ ๊ฐ์ด ์ฌ๋ฌ ์์ ์์น๋ฅผ ์ง์ ํ ์๋ ์๋ค.
basePackageClasses
: ์ง์ ํ ํด๋์ค์ ํจํค์ง๋ฅผ ํ์ ์์ ์์น๋ก ์ง์ ํ๋ค.
โ ์ง์ ํ์ง ์์ผ๋ฉด @ComponentScan
์ด ๋ถ์ ์ค์ ์ ๋ณด ํด๋์ค์ ํจํค์ง๊ฐ ์์ ์์น๊ฐ ๋๋ค.
โ ๊ถ์ฅ ๋ฐฉ๋ฒ: ํจํค์ง ์์น๋ฅผ ์ง์ ํ์ง ์๊ณ ์ค์ ์ ๋ณด ํด๋์ค์ ์์น๋ฅผ ํ๋ก์ ํธ ์ต์๋จ์ ๋๋ค(์คํ๋ง๋ถํธ)
์ปดํฌ๋ํธ ์ค์บ ๊ธฐ๋ณธ ๋์
์ปดํฌ๋ํธ ์ค์บ์ ์ค์บ ๋์
@Component
: ์ปดํฌ๋ํธ ์ค์บ์์ ์ฌ์ฉ@Controlller
: ์คํ๋ง MVC ์ปจํธ๋กค๋ฌ์์ ์ฌ์ฉ@Service
: ์คํ๋ง ๋น์ฆ๋์ค ๋ก์ง์์ ์ฌ์ฉ@Repository
: ์คํ๋ง ๋ฐ์ดํฐ ์ ๊ทผ ๊ณ์ธต์์ ์ฌ์ฉ@Configuration
: ์คํ๋ง ์ค์ ์ ๋ณด์์ ์ฌ์ฉ
๊ธฐ๋ณธ์ ์ผ๋ก ์ ๋ ธํ ์ด์ ์ ์์๊ด๊ณ๊ฐ ์๋ค -> ์์ ๊ฐ์ ๊ธฐ๋ฅ์ ์๋ฐ๊ฐ ์๋๋ผ ์คํ๋ง์์ ์์ฒด์ ์ผ๋ก ์ง์ํ๋ ๊ธฐ๋ฅ
โป ์ฐธ๊ณ : ์ ๋ ธํ ์ด์ ์ ๊ธฐ๋ฅ
@Controller
: ์คํ๋ง MVC ์ปจํธ๋กค๋ฌ๋ก ์ธ์@Repository
: ์คํ๋ง ๋ฐ์ดํฐ ์ ๊ทผ ๊ณ์ธต์ผ๋ก ์ธ์ํ๊ณ , ๋ฐ์ดํฐ ๊ณ์ธต์ ์์ธ๋ฅผ ์คํ๋ง ์์ธ๋ก ๋ณํ@Configuration
: ์คํ๋ง ์ค์ ์ ๋ณด๋ก ์ธ์ํ๊ณ , ์คํ๋ง ๋น์ด ์ฑ๊ธํค์ ์ ์งํ๋๋ก ์ถ๊ฐ ์ฒ๋ฆฌ@Service
: ํน๋ณํ ์ฒ๋ฆฌ๋ฅผ ํ์ง ์์ง๋ง, ๋์ ๊ฐ๋ฐ์๋ค์ด ํต์ฌ ๋น์ฆ๋์ค ๋ก์ง์ด ์ฌ๊ธฐ์ ์๊ฒ ๊ตฌ๋ ๋ผ๊ณ ๋น์ฆ๋์ค ๊ณ์ธต์ ์ธ์ํ๋๋ก ๋์
ํํฐ
includeFilters
: ์ปดํฌ๋ํธ ์ค์บ ๋์์ ์ถ๊ฐ๋ก ์ง์ excludeFilters
: ์ปดํฌ๋ํธ ์ค์บ์์ ์ ์ธํ ๋์์ ์ง์
// ์ปดํฌ๋ํธ ์ค์บ ๋์์์ ์ ์ธํ ์ ๋
ธํ
์ด์
package hello.core.scan.filter;
import java.lang.annotation.*;
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface MyExcludeComponent {
}
// ์ปดํฌ๋ํธ ์ค์บ ๋์์ ์ถ๊ฐํ ์ ๋
ธํ
์ด์
package hello.core.scan.filter;
import java.lang.annotation.*;
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface MyIncludeComponent {
}
// ์ปดํฌ๋ํธ ์ค์บ ๋์์ ์ถ๊ฐํ ํด๋์ค
package hello.core.scan.filter;
@MyIncludeComponent
public class BeanA {
}
// ์ปดํฌ๋ํธ ์ค์บ ๋์์์ ์ ์ธํ ํด๋์ค
package hello.core.scan.filter;
@MyExcludeComponent
public class BeanB {
}
// ํ
์คํธ์ฝ๋
public class ComponentFilterAppConfigTest {
@Test
void filterScan() {
AnnotationConfigApplicationContext ac = new AnnotationConfigApplicationContext(ComponentFilterAppConfig.class);
BeanA beanA = ac.getBean("beanA", BeanA.class);
Assertions.assertThat(beanA).isNotNull();
org.junit.jupiter.api.Assertions.assertThrows(
NoSuchBeanDefinitionException.class,
() -> ac.getBean("beanB", BeanB.class));
}
@Configuration
@ComponentScan(
includeFilters = @ComponentScan.Filter(type = FilterType.ANNOTATION, classes = MyIncludeComponent.class),
excludeFilters = @ComponentScan.Filter(type = FilterType.ANNOTATION, classes = MyExcludeComponent.class)
)
static class ComponentFilterAppConfig{
}
}
ํ ์คํธ ์ฝ๋๋ฅผ ์คํํด๋ณด๋ฉด BeanA๋ ๋ฑ๋ก๋๊ณ BeanB๋ ๋ฑ๋ก๋์ง ์๋๋ค.
FilterType ์ต์
5๊ฐ์ง ์ต์ ์กด์ฌ
- ANNOTATION: ๊ธฐ๋ณธ๊ฐ, ์ ๋ ธํ ์ด์ ์ ์ธ์ํด์ ๋์ํ๋ค. ex) org.example.SomeAnnotation
- ASSIGNABLE_TYPE: ์ง์ ํ ํ์ ๊ณผ ์์ ํ์ ์ ์ธ์ํด์ ๋์ํ๋ค. ex) org.example.SomeClass
- ASPECTJ: AspectJ ํจํด ์ฌ์ฉ ex) org.example..*Service+
- REGEX: ์ ๊ท ํํ์ ex) org.example.Default.*
- CUSTOM: TypeFilter ์ด๋ผ๋ ์ธํฐํ์ด์ค๋ฅผ ๊ตฌํํด์ ์ฒ๋ฆฌ ex) org.example.MyTypeFilter
์ผ๋จ์ ๊ธฐ๋ณธ ์ค์ ์ผ๋ก ์ฌ์ฉํ๋ ๊ฒ ๊ถ์ฅ!
์ค๋ณต ๋ฑ๋ก๊ณผ ์ถฉ๋
์๋ ๋น ๋ฑ๋ก vs ์๋ ๋น ๋ฑ๋ก
ConflictingBeanDefinitionException
์์ธ ๋ฐ์
์๋ ๋น ๋ฑ๋ก vs ์๋ ๋น ๋ฑ๋ก
์๋ ๋น ๋ฑ๋ก์ด ์ฐ์ ๊ถ์ ๊ฐ์ง๋ ๊ถ์ฅํ์ง๋ ์๋๋ค!!
์คํ๋ง๋ถํธ์์๋ ์๋ฌ์ฒ๋ฆฌ!
'โญ Personal_Study > Spring' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ
๋น ์๋ช ์ฃผ๊ธฐ ์ฝ๋ฐฑ (0) | 2023.01.10 |
---|---|
์์กด๊ด๊ณ ์๋ ์ฃผ์ (1) | 2023.01.09 |
Singleton Container (0) | 2023.01.06 |
์คํ๋ง ์ปจํ ์ด๋ & Bean ์กฐํ (0) | 2023.01.05 |
์ ์ด์ ์ญ์ (IoC) & ์์กด์ฑ ์ฃผ์ (DI) (1) | 2023.01.01 |
๋๊ธ