2024. 8. 8. 16:54ㆍ스프링
2024/08/08
※ IoC 컨테이너와 Bean에 대해 알아보자.
▶ Spring IoC 컨테이너
👉 지난 포스팅에서 DI를 사용했을 때의 장점을 알아보았다.
그런데 DI를 사용하기 위해서는 객체 생성이 우선되어야 했다.
그렇다면 언제❓, 어디서❓, 누가❓객체 생성을 해야 할까?
바로 Spring 프레임워크가 필요한 객체를 생성하고 관리하는 역할을 대신 해준다.
● 빈(Bean) : Spring이 관리하는 객체
● Spring IoC 컨테이너 : 'Bean'을 모아둔 컨테이너
▶ Spring 'Bean' 등록 방법
● @Component
○ 'Bean'으로 등록하고자 하는 클래스 위에 설정
@Component
public class MemoService { ... }
○ Spring 서버가 뜰 때 IoC 컨테이너에 'Bean'을 저장한다.
- @Component가 설정된 클래스에 대해서 Spring이 하는 일 확인하기
// 1. MemoService 객체 생성
MemoService memoService = new MemoService();
// 2. Spring IoC 컨테이너에 Bean (memoService) 저장
// memoService -> Spring IoC 컨테이너
- Spring 'Bean' 이름 : 클래스의 앞글자만 소문자로 변경
EX) public class MemoService ➡️ memoService
○ 'Bean' 아이콘 확인 ➡️ 스프링 IoC에서 관리할 'Bean' 클래스라는 표시(인텔리제이의 경우)
● @ComponentScan
○ Spring 서버가 뜰 때 @ComponentScan에 설정해 준 packages 위치와 하위 packages 들을 전부 확인하여
@Component가 설정된 클래스들을 ‘Bean’으로 등록한다.
@Configuration
@ComponentScan(basePackages = "com.sparta.memo")
class BeanConfig { ... }
○ @SpringBootApplication에 의해 default 설정되어 있다.
EX) com.sparta.memo/MemoApplication.java
▶ Spring 'Bean' 사용 방법
● @Autowired
○ 필드 위에 @Autowired
@Component
public class MemoService {
@Autowired
private MemoRepository memoRepository;
// ...
}
- Spring에서 IoC 컨테이너에 저장된 memoRepository ‘Bean’을 해당 필드에 DI 즉, 의존성을 주입해준다.
○ 'Bean'을 주입할 때 사용할 메서드 위에 @Autowired
@Component
public class MemoService {
private final MemoRepository memoRepository;
@Autowired
public MemoService(MemoRepository memoRepository) {
this.memoRepository = memoRepository;
}
// ...
}
- 객체의 불변성을 확보할 수 있기 때문에 일반적으로는 생성자를 사용하여 DI하는 것이 좋다.
- set… Method를 만들고 @Autowired를 적용하여 DI 할 수도 있다.
○ @Autowired 적용 조건
- Spring IoC 컨테이너에 의해 관리되는 클래스에서만 가능
✅ 당연한 말이지만 Spring IoC 컨테이너에 의해 관리되는 ‘Bean’객체만 DI에 사용될 수 있다.
○ @Autowired 생략 조건
- Spring 4.3 버젼 부터 @Autowired 생략 가능
- 단, 생성자 선언이 1개일 때만 생략 가능
public class A {
public A(B b) { ... }
}
■ 오버로딩된 생성자들
public class A {
@Autowired // 생략 불가
public A(B b) { ... }
@Autowired // 생략 불가
public A(B b, C c) { ... }
}
- Lombok의 @RequiredArgsConstructor를 사용하면 다음과 같이 코딩 가능
@Component
@RequiredArgsConstructor // final로 선언된 멤버 변수를 파라미터로 사용하여 생성자를 자동으로 생성합니다.
public class MemoService {
private final MemoRepository memoRepository;
// public MemoService(MemoRepository memoRepository) {
// this.memoRepository = memoRepository;
// }
...
}
● ApplicationContext
○ ApplicationContext는 BeanFactory등을 상속하여 기능을 확장한 Container
- BeanFactory는 ‘Bean’ 의 생성, 관계 설정 등의 제어를 담당하는 IoC 객체
○ 스프링 IoC 컨테이너에서 ‘Bean’을 수동으로 가져오는 방법
@Component
public class MemoService {
private final MemoRepository memoRepository;
public MemoService(ApplicationContext context) {
// 1.'Bean' 이름으로 가져오기
MemoRepository memoRepository = (MemoRepository) context.getBean("memoRepository");
// 2.'Bean' 클래스 형식으로 가져오기
// MemoRepository memoRepository = context.getBean(MemoRepository.class);
this.memoRepository = memoRepository;
}
...
}
● 3 Layer Annotation
○ Spring 3 Layer Annotation은 Controller, Service, Repository의 역할로 구분된 클래스들을 ‘Bean’으로 등록할 때
해당 ‘Bean’ 클래스의 역할을 명시하기위해 사용된다.
1. @Controller, @RestController
2. @Service
3. @Repository
○ 앞으로는 @Component가 아닌 3 Layer Annotation을 사용해서 ‘Bean’으로 등록하자.
💡 Spring 3 Layer Annotation은 모두 @Component가 추가되어있다.
오늘은 스프링의 기본 개념인 IoC 컨테이너와 Bean에 대해 알아보았습니다.
※ 위 이미지들은 스파르타코딩클럽에 저작권이 있으므로 무단 도용 금지 및 상업 목적으로 사용할 수 없습니다.
'스프링' 카테고리의 다른 글
스프링 - 영속성 컨텍스트란? (0) | 2024.08.13 |
---|---|
스프링 - Entity란? (0) | 2024.08.12 |
스프링 - Spring Data JPA란 무엇일까? (0) | 2024.08.09 |
쿠키와 세션이란 무엇일까? (0) | 2024.08.05 |
스프링 - IoC와 DI의 개념 (0) | 2024.08.02 |