0. 개요
- 이전 포스팅에서 Bean 자동 등록에 대해서 알아보았다.
- 이번 포스팅에서는 Bean 자동 등록의 핵심인 Component Scan에 대해서 알아보자.
1. @ComponentScan의 동작원리
a) @ComponentScan의 탐색 위치 설정
- @ComponentScan이 붙은 클래스의 위치를 기반으로 Bean을 찾아 Spring Container에 등록한다.
- 여기서 말하는 클래스의 위치란, 클래스를 생성하면 클래스 상단에 자동으로 부여되는 package경로를 의미한다.
package hello.spring;
public class HelloSpring {}
- 이처럼 해당 클래스의 패키지 경로부터 하위 경로까지, 모든 클래스의 Bean을 탐색한다.
- 더불어, 옵션을 사용하면 @ComponentScan의 탐색 범위를 직접 지정할 수 있다.
// 1. 단일 경로 설정
@ComponentScan(basePackage = "경로")
// 2. 다수 경로 설정
@ComponentScan(basePackage = "경로1", "경로2")
// 3. 특정 파일을 이용하여, 해당 위치부터 탐색 경로를 설정
@ComponentScan(basePackageClass = 파일명1.class, 파일명2.class)
- 위의 예시처럼, basePackage, basePackageClass 옵션을 사용하여 직접 탐색 경로를 지정할 수 있다.
- 하지만, Spring에서는 특정 탐색 경로를 설정하는 방식보다 Default 방식을 권장한다.
b) @SpringBootApplication
- Spring은 기본적으로 프로젝트의 root경로부터 ComponentScan을 수행한다.
- 그렇다면 Spring은 프로젝트의 root 경로를 어떻게 알까?
- Spring 프로젝트를 생성하면, 프로젝트의 root 위치에 main() 메서드를 가진 클래스가 생성된다.
- 이 클래스에는 @SpringBootApplication이 존재하는데, 이 어노테이션의 내부에는 @ComponentScan이 포함되어 있다.
- 위의 사진은 @SpringBootApplication의 클래스 파일이다.
- 사진에서 볼 수 있듯이, @SpringBootApplication 내부에는 @ComponentScan이 존재한다.
- 앞서 @ComponentScan이 붙은 클래스의 패키지 경로를 기반으로 탐색을 시작한다고 했다.
- @SpringBootApplication은 root 경로에 있으며, 이 어노테이션 내부에는 @ComponentScan이 있으므로,
Spring은 root 위치부터의 ComponentScan을 시작하는 것이다.
c) @ComponentScan의 대상과 부가기능
- @Bean 또는 @Component 외에도 ComponentScan의 대상이 되는 다양한 어노테이션이 있다.
- 어노테이션 클래스에 @Component를 포함한다면 Component Scan의 대상으로 인식되기 때문이다.
- 아래에 소개할 어노테이션은 Component Scan의 대상으로, Spring Container에 Bean으로 등록된다.
- 더불어, 각 어노테이션은 부가적인 기능을 제공한다.
→ @Controller: Spring은 해당 클래스를 Controller로 인식한다.
→ @Repository: Spring은 해당 클래스를 데이터 접근 계층으로 인식하고, 데이터 계층의 예외를 spring 예외로 변환한다.
→ @Service: 개발자 간의 Semantic annotation으로, 비즈니즈 로직을 처리하는 역할임을 명시한다.
→ @Configuration: Spring은 해당 클래스를 설정 정보로 인식하고, @Bean을 찾아 Singleton으로 관리한다.
- 다음 사진은 각 어노테이션의 클래스 파일이다. 모두 내부에 @Component를 보유하고 있다.
2. ComponentScan에서 제외 또는 추가하는 방법
- @ComponentScan은 다양한 옵션을 제공한다. 그중 하나가 ComponentScan에서 제외/추가하는 방법이다.
- 자주 필요로 하는 기능은 아니지만, 간단히 알아보자.
a) includeFilters & excludeFilters
- includeFilters 옵션은 ComponentScan에 포함시키는 기능이다.
- ComponentScan의 대상이 아니지만, ComponentScan에 포함시켜야 하는 경우 사용한다.
@ComponentScan(
includeFilters = {
@Filter(type = FilterType.상수, classes = 클래스명.class) })
- excludeFilters 옵션은 ComponentScan에서 제외시키는 기능이다.
- ComponentScan의 대상이지만, ComponentScan에서 제외시켜야 하는 경우 사용한다.
@ComponentScan(
excludeFilters = {
@Filter(type = FilterType.상수, classes = 클래스명.class) })
- type은 ComponentScan에 포함/제외 기준 설정이다. 이 값은 Spring에서 상수로 제공한다.
- classes는 ComponentScan에 포함/제외할 특정 클래스를 명시하는 설정이다.
b) FilterType의 5가지 옵션
- type 옵션에 할당되는 상수는 다음 5가지이다.
→ FilterType.ANNOTATION: annotation을 기준으로 인식한다. (default 설정이므로 생략 가능)
→ FilterType.ASSIGNABLE_TYPE: 지정한 타입과 자식 타입까지 인식한다.
→ FilterType.ASPECTJ: AspectJ 패턴을 사용
→ FilterType.REGEX: 정규표현식을 사용
→ FilterType.CUSTOM: TypeFilter라는 인터페이스를 구현하여 사용한다.
'Back-end > Spring 개념' 카테고리의 다른 글
11. Dependency Injection 기본개념 (0) | 2022.02.10 |
---|---|
10. Bean 자동 vs 수동 등록 (0) | 2022.02.09 |
8. Bean 자동 등록 (0) | 2022.02.07 |
7. Singleton Container (0) | 2022.02.02 |
6. Spring Container의 다형성 (0) | 2022.02.01 |
댓글