지금까지는 Service Interface를 따로 두지 않고 Service 클래스를 단일로 사용하는 구조로 개발을 했다.
그런데 다른 분들의 코드나 강의에서 나오는 코드들 중 Service - ServiceImpl 구조가 많이 보였다.
많은 분들이 쓰신다면 저 구조로 설계를 하는 것이 맞는 것이겠지만 왜 저런 구조로 쓰는지 알지도 못하면서
아무 생각 없이 저 구조를 사용한다면 의미가 없다는 생각이 들어 관련 블로그들을 보며 정리해보게됐다.
Service interface와 ServiceImpl class 구조를 사용하는 이유
- 인터페이스와 구현체의 분리를 통해 특정 기술이나 외부환경에 독립적으로 보다 자유로운 확장이 가능하다.
- 구현체 클래스를 변경하거나 확장해도 이를 사용하는 클라이언트의 코드에 영향을 주지 않도록 느슨한 결합을 유지하여 각 기능 간 의존관계를 최소화 함으로써 기능의 변화에도 유연한 대처가 가능하다.
- 모듈화를 통해 어디서든 사용할 수 있도록 재사용성을 높인다.
- 객체 지향의 특징 중 하나인 다형성과 객체지향의 다섯가지 원칙 중 하나인 OCP 원칙을 가장 잘 실현해주는 설계방식이다.
- OCP (Open Closed Principle)
- 개방, 폐쇄 원칙이라고 하며
- 소프트웨어 개체(클래스, 모듈, 함수 등)는 확장에 대해 열려있어야 하고, 수정에 대해서는 닫혀있어야 한다.
- 는 프로그래밍 원칙이다.
- OCP (Open Closed Principle)
- 위 추상화를 통한 구현 방식의 단점
- 코드 구조가 복잡해지고, 복잡해진 구조만큼 코드를 분석하고 확인하는 과정에서 인터페이스를 거쳐 구현체들을 확인해야하는 번거로움이 생긴다.
- 대부분의 프로젝트는 인터페이스와 구현체가 1:1로 만들어져 사용되고 있기에 인터페이스를 사용하는 이점을 가지지 못하지만 관습적으로 추상화를 적용한다.
이렇게 Service & ServiceImpl 구조에 대해 알아봤는데 의문을 해결하지는 못했다.
결국 인터페이스와 구현체가 1:1로 만들어지는 구조에서 굳이 추상화를 통한 구현 방식을 택해야할까?
이것도 결국은 프로젝트를 설계하는 사람이 어떤 방식으로 설계를 할지 선택하는 것이라고 생각한다.
하지만 사용하든 사용하지 않든 이에 대한 이유와 근거에 대해 알고 있고, 설명할 수 있으면 되지않을까
관습적인 추상화 방식을 적용해야한다는 입장의 의견
- 객체에 대한 설계와 이를 구현한 코드는 언제든 변할 수 있습니다. 그렇기 때문에 개발자는 이를 대비해야합니다. 지금 만들어서 사용중인 인터페이스와 구현체 클래스가 1:1 관계를 맺고 있을지 모르지만 서비스가 커지고 변화함에 따라서 얼마든지 구현체 클래스는 확장될 가능성을 가지고 있습니다. 그렇기 때문에 이러한 구조를 통해 미래의 변화에 유연하게 대처할 수 있도록 대비해야합니다. (토비의 스프링 3.1 1장 중)
- 이러한 구조는 협업에서 이점으로 작용될 수 있습니다. 프로젝트를 시작할 때 설계자가 프로젝트의 큰 뼈대를 구성하고, 나머지 작업자들은 그에 맞는 실제 구현을 하게되는 경우가 있습니다. 이때 함수명, 리턴, 파라미터 등을 설계자가 만들어놓은 인터페이스에 맞춰 코딩할 수 있습니다. 이처럼 인터페이스를 누군가 작성하고 실제 구현은 다른사람이 할 수 있는 분할의 기능도 협업에서의 이점이 될 수 있습니다.
결론
이렇게 궁금했었던 Service & ServiceImpl 구조에 대해 공부해봤다.
해당 구조의 이점도 확실히 알았지만 대부분은 1:1 관계로 존재하기에 관습적으로 사용한다고해서 무조건 추상화 방식을 적용할 필요는 없어보인다. 본인이 또는 팀내에서 어떤 목적을 두고 프로그램을 만드는지에 따라 알맞게 활용하면 될 것 같다.
'TIL' 카테고리의 다른 글
JPA - QueryDSL을 이용한 동적쿼리 (0) | 2024.11.15 |
---|---|
JPA - QueryDSL (1) | 2024.11.15 |
JPA - 복합키와 식별 관계 매핑 (0) | 2024.11.12 |
미리 서명된 URL(Pre-signed url) 사용해보기 (0) | 2024.11.11 |
GCS를 이용한 이미지 업로드 기능 구현 (2) | 2024.11.08 |