새소식

Software Engineering

싱글턴의 진짜 문제점

  • -

많은 사람들이 싱글턴은 안티 패턴이라는 얘기를 한다. 그 이유로 가장 많이 이야기하는 것이 testability이다. 맞는 말이다. 싱글턴 객체는 스터빙할 수 없기 때문에 테스팅을 어렵게 만든다. 최근 TDD와 Unit 테스팅을 강조하는 개발 조직이 많아졌기 때문에 이 부분이 가장 크게 두각되는 것 같다. 하지만 Unit 테스팅을 하지 않는다면?

그리고 또 많이 이야기하는 부분이 SOLID 원칙을 위반한다는 이야기다. 이 역시 맞는 말이다. 하지만 so what? 그게 실제로 어떤 문제를 발생시킨다는 건가?

또 상속을 할 수 없다는 이야기도 한다. 하지만 굳이 상속을 할 필요가 없다면?

Unit 테스트를 작성하지도 않고 SOLID 원칙도 무시하며 상속도 굳이 사용할 필요가 없는 경우라면 싱글턴을 쓰지 말아야 한다는 것을 무슨 이유로 설득할 수 있겠는가? (물론 그런 팀에서 일해야 한다는 건 너무나 불행한 일이겠지만...)

싱글턴을 사용하지 말아야 할 진짜 이유는 무엇일까? 나는 그 이유를 조슈아 캐리에브스키의 저서 <패턴을 활용한 리팩터링>에 나와 있는 다음 문구에 잘 나타나 있다고 생각한다.

Singleton 패턴에 대한 Kent Beck의 견해
싱글턴이 야기하는 진짜 문제는 어떤 객체의 가시범위를 어떻게 정할지를 크게 고민하지 않아도 되게 만든다는 점이다. 객체의 노출 영역과 보호 영역에 대한 균형을 적절하게 맞추는 것은 융통성을 유지하기 위한 필수 요건이다.

 

객체의 가시범위를 고민하지 않고 전역에서 접근할 수 있도록 하면 그 객체가 언제 만들어져서 어디에서 참조되고 있을지 예측하기 힘들어지고 이는 객체의 유연성을 떨어뜨려서 수정하기 어렵게 만든다는 말이다.

예를 들어 어떤 메소드를 수정하려고 할 때 보통 영향 범위를 파악하기 위해 그 메소드를 참조하는 곳을 찾아보고 원하는 대로 수정해도 문제가 없는지 파악하는 과정을 거치게 되는데, 이 때 이 메소드를 가지고 있는 객체가 싱글턴이라면 이 메소드를 참조하는 곳이 애플리케이션 전체에 퍼져있을 수 있다. 이것은 하나의 메소드 수정의 영향범위가 앱 전체로 늘어나게 되는 것(shotgun surgery)이고 이 메소드를 참조하는 객체 중에 또 싱글턴이 있다면, 그리고 또 그 객체를 싱글턴이 참조한다면, ... 메소드 하나의 수정이 앱 전체에 막대한 영향을 미치게 되고 결국 개발자는 이 메소드를 수정하는 것을 포기하고 싶은 유혹에 빠지게 된다. 수정을 겨우 겨우 한다고 해도 QA팀에서 전수 테스트를 해야만 하는 상황에 직면하게 된다. 이러한 문제는 결국 리팩토링을 수시로 하는 것이 아니라 큰 맘 먹고 해야하는 것으로 만들고, 차라리 다시 작성하는 것이 낫다는 말이 나오게 만든다. 이것을 다른 말로 하면 프로그램의 유연성이나 융통성이 떨어진다고 표현하는 것이다.

게다가 대부분의 경우 싱글턴을 사용하면서 라이프 사이클에 대해 고민하지 않기 때문에 한번 생성된 객체는 더이상 필요가 없어져도 소멸시키지 않는다. 이는 메모리 효율성 측면에서도 매우 비효율적이다. 따라서 누군가 싱글턴은 객체를 하나만 만들기 때문에 메모리를 효율적으로 사용할 수 있다고 말한다면 그것은 미신에 가깝다고 말하고 싶다.

반응형

'Software Engineering' 카테고리의 다른 글

MVVM과 Clean Architecture  (1) 2023.12.05
Robert C. Martin의 Architecture  (0) 2019.12.05
Contents

포스팅 주소를 복사했습니다

이 글이 도움이 되었다면 공감 부탁드립니다.