싱글톤
블로그에 정리하는 느낌 내려면 정확한 정의가 필요할 것 같아서 방금 검색해보고 왔다.
'하나'의 인스턴스만 생성하여 사용하는 디자인 패턴
어라? static이랑 겹치는 것 같은데? 하고 검색 한번 더 해봤다. static으로 만들면 가장 큰 차이점은 인터페이스를 구현할 수 없어서
다형성을 실현할 수 없다.
본격적으로 시작하면 웹 애플리케이션은 클라이언트의 요청이 끊임없이 들어온다고 한다. 예를 들어 주문 서비스 요청이 1000번 들어왔다. 이때 OrderServiceImpl을 1000개 만들어야 할까? 이런 메모리 낭비를 방지하기 위해 웹 애플리케이션 개발에서 싱글톤 패턴이 중요하다. 강의에서 싱글톤 패턴을 적용한 클래스를 만드는 방법을 하나 소개해 주었다. 일단 자기 자신을 static으로 선언한다. 정의를 다시 확인해보자. 무조건 1개의 인스턴스만 존재하여야 한다. 1개라는 조건을 static으로 자기 자신이 선언하여 메모리에 올려둠으로써 충족했다. 그렇다면 이제 더 이상 인스턴스는 생성되면 안 된다. 외부에서의 생성을 막기 위해 생성자를 private으로 작성해두면 된다. (외부에서 new를 막아주니까 인스턴스가 더 이상 생성될 수 없다.) 여기까지가 방법이다. 하지만 설명과 같이 작성하면 구체 클래스에 의존하고 코드도 길어지고 테스트도 어려워지고 문제가 많다. 하지만 우리는? 걱정할 필요가 없다. 위의 방법을 사용하지 않고 그대로 스프링 컨테이너에 등록만 해두면 스프링이 알.아.서 싱글톤 패턴으로 객체를 관리해준다.
(실습에서 인스턴스가 같은지 안같은지 테스트하면서 배운 새로운 함수. isSameAs => 객체들의 주소 값이 같은지 비교해준다 ==와 같은 의미 . isEqualTo는 객체의 멤버 변수의 값이 같은지 비교해준다.)
스프링이 싱글톤 패턴으로 만들어주지만 개발자가 주의해야 할 부분이 있다. 상태를 유지(stateful)하게 설계하면 안된다.
무상태(stateless)로 설계하여야 한다. 예를 들면 MemberSerivce 클래스 안에 String clientName을 작성했다. 주문이 여러 개 들어와도
싱글톤 패턴에 의해서 MemberService 인스턴스는 1개만 생성된다. 구체적인 상황을 부여하면
- te__ho가 주문을 하면서 clientName을 te__ho로 설정
- dmaolon이 주문을 하면서 clientName을 dmaolon으로 설정
- te__ho가 getclientName() 메서드를 호출했다.
이때 리턴 값은???????? dmaolon이다. 1개의 인스턴스를 여러 클라이언트가 공유하기 때문에 특정 클라이언트가 값을 변경할 수 있는 공유 필드는 존재해서는 안된다. 이 문제가 실무에서 가격관련 하여 일어나면 난리법석이다. 해결 방법은 공유되지 않는 지역변수, 파라미터,
ThreadLocal 사용하기 등이 있다. (ThreadLocal 찾아봤는데 쓰레드 개념부터 안 잡혀있어서 일단 미뤄본다.)
AppConfig의 코드들을 보면 순수 자바 코드에 의해 new가 여러번 되는 클래스가 존재한다. 이러면 싱글 톤을 위반하게 되는 거 아닌가?
@Configuration이 알아서 다 처리해준다. AppConfig도 빈에 등록되는데 이때 등록되는 클래스는 우리가 작성한 AppConfig가 아닌
ClGIB라는 바이트조작라이브러리를 사용하여 AppConfig를 상속한 다른 클래스(AppConfig@CLGIB)를 빈에 등록한다. AppConfig가 부모 타입이므로 AppConfig로 AppConfig@CLGIB도 조회할 수 있다. (부모를 조회할 시 자식도 모두 조회 가능. 이라고 전 포스트에
작성하였다.) @Configuration 대신 @Bean을 작성하면 new가 여러 번 호출되어 인스턴스를 여러 개 만든다.
결론은? 그냥 @Configuration쓰면 스프링이 알아서 다 해준다.
'Spring' 카테고리의 다른 글
[Spring] 의존관계 자동 주입 방법 & 옵션 처리 & LOMBOK(롬복) (0) | 2022.08.01 |
---|---|
[Spring] @ComponentScan & @Autowired (의존관계 자동 주입) (1) | 2022.07.26 |
[Spring] 스프링 컨테이너 & 스프링 빈 조회 (3) | 2022.07.20 |
[Spring] AppConfig (0) | 2022.07.16 |
[Spring] Test (0) | 2022.07.16 |