Back/Spring
Spring - Singleton(싱글톤)
by Hyeon_
2022. 1. 5.
Spring - Singleton
- 스프링 컨테이너는 빈을 생성할 때 싱글톤 패턴을 적용하지 않아도 항상 클래스당 1개의 인스턴스만 생성한다.(default)
- singleton 속성 변경 가능
- <bean> 태그의 scope 속성을 이용하여 빈이 싱글톤으로 생성되게 할지 아니면 요청할 때마다 생성되게 할지 설정 가능
- singleton : 컨테이너에 한 개의 인스턴스만 생성(기본 값)
- prototype : 빈을 요청할 때마다 인스턴스 생성
- thread : 쓰레드 별로 생성
- request / session / application scope 있음
싱글톤(Singleton) 확인
- MemberMain 클래스에서 member2 객체(인스턴스) 생성하고 앞에서 생성한 member와 동일한지 확인
Annotation을 이용한 DI
- xml 설정 파일에서 <bean> 태그를 이용해서 설정하였던 빈 설정을 Annotation(메타데이터)을 이용하여 자바 코드에서 설정
- ex) xml 설정 파일에서 <bean>을 설정하지 않고 스프링이 자바 코드를 읽어서 클래스에 @Component 어노테이션이 붙은 클래스를 객체화(bean) 설정
- AI 클래스의 객체를 A2 클래스의 객체로 변경하려면 AI 클래스에서 @Component를 제거하고 A2 클래스에 @Component를 붙이면 됨
- @Autowired 어노테이션을 사용하여 bean 자동 주입
xml 설정 파일에 context 네임스페이스 추가
- 빈 설정을 위한 어노테이션을 사용하기 위해서는 설정 파일에 context 네임스페이스가 추가되어있어야 함.
- <context:component-scan> 태그 이용하여 빈으로 등록될 클래스 패키지 지정
- 자바 소스 코드에서 @Component로 등록된 클래스를 찾아서 클래스를 객체화(빈 설정)
스프링에서 사용하는 Annotation 종류
- DI 관련 Annotation
@Autowired
/ @Inject
@Qualifier
@Resource
- 빈 생성 관련 Annotation
@Component
- @Controller
- @Service
- @Repository
@Configuration
DI 관련 Annotation
- xml 설정 파일에 있는 <bean>에 대해 DI하거나 자바 코드에서 생성된 bean에 대해 DI 할 수 있음
- @Autowired
- 타입을 기준으로 의존성 주입
- 스프링 빈에 의존하는 다른 빈을 자동으로 주입할 때 사용
- 스프링에서 지원
- @Inject : @Autowired와 동일(자바에서 지원)
- @Qualifier : 특정 빈의 이름을 지정
- 동일한 interface를 구현한 클래스가 여러 개 있는 경우 사용하고자 하는 특정 빈의 이름을 지정할 때 사용
- @Resource
- @Autowired와 @Qualifier를 같이 사용하는 것과 동일
- 자바에서 지원
DI 관련 Annotation 예제
- 프로젝트 생성
- 패키지 : com.di.spring_di_annotation
- 클래스
- INameService
- BNameService - INameService 인터페이스 구현
- NameController
- NameMain
INameService
public interface INameService {
public String showName(String name);
}
BNameService
public class BNameService implements INameService{
@Override
public String showName(String name) {
System.out.println("BNameService showName() 메소드");
String myName = "내 이름은 " + name + " 입니다.";
return myName;
}
}
NameController
public class NameController {
// 인터페이스 타입으로 선언
// @Autowired 어노테이션 사용해서 nameService 빈을 자동으로 주입
// 해당 타입의 빈으 찾아서 필드(변수)에 주입
@Autowired
INameService nameService;
public void setNameService(INameService nameService) {
this.nameService = nameService;
}
public void show(String name) {
System.out.println("NameController : " + nameService.showName(name));
}
}
NameMain
public class NameMain {
public static void main(String[] args) {
AbstractApplicationContext context = new GenericXmlApplicationContext("application-context.xml");
NameController controller = context.getBean("nameController", NameController.class);
controller.show("강길동");
context.close();
}
}
@Qualifier 어노테이션
NameController
package com.di.spring_di_annotation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
public class NameController {
// 인터페이스 타입으로 선언
// @Autowired 어노테이션 사용해서 nameService 빈을 자동으로 주입
// 해당 타입의 빈으 찾아서 필드(변수)에 주입
@Autowired
@Qualifier("anotherNameService")
INameService nameService;
public void setNameService(INameService nameService) {
this.nameService = nameService;
}
public void show(String name) {
System.out.println("NameController : " + nameService.showName(name));
}
}
@Resource 어노테이션
- @Autowired와 @Qualifier를 같이 사용하는 것과 동일한 결과
- name 속성을 이용해서 빈 이름 직접 지정
- @Resource(name="anotherNameService")
- name 속성을 생랴갛면 속성의 이름과 동일한 빈을 찾음
- 단, Java 9버전에서는 사용할 수 없음
- 자바에서 지원
- pom.xml에서 <dependency> 추가해야 함
- javax.annotation dependency 추가
@Autowired 어노테이션의 required 속성
- 의존 객체를 주입하지 않아도 될 때 사용
- @Autowired(required=false)
- xml 파일에 <bean>이 존재하지 않아도 오류 발생
- @Autowired
@Autowired 위치
- 필드(field) 앞
- 생성자 앞
- Setter 메소드 앞