티스토리 뷰
💧 SOLID 원칙
SOLID 원칙은 객체지향 설계 다섯 가지 원칙의 앞글자를 따서 만든 용어로, 로버트 C. 마틴(Robert C. Martin)에 의해 제시되었습니다.
- 단일 책임 원칙 (Single Responsibility Principle, SRP)
- 개방-폐쇄 원칙 (Open-Closed Principle, OCP)
- 리스코프 치환 원칙 (Liskov Substitution Principle, LSP)
- 인터페이스 분리 원칙 (Interface Segregation Principle, ISP)
- 의존성 역전 원칙 (Dependency Inversion Principle, DIP)
이 다섯 가지 원칙들은 반드시 지켜야 하는 의무사항은 아니지만, 좋은 설계를 위해 지향해야 하는 원칙들입니다.
💯 좋은 설계란?
그렇다면 좋은 설계란 무엇일까요? 좋은 설계가 있다면 나쁜 설계도 있을 것입니다. 나쁜 설계에 대해 먼저 알아보겠습니다.
나쁜 설계
나쁜 설계는 모듈 내부의 낮은 응집도를 가지고 있습니다. 여기서 모듈의 정의는 맥락에 따라 다를 수 있지만, 파일 또는 폴더로 구조화된 코드의 묶음으로 정의해 보겠습니다. 그림을 보시면 모듈 A의 기능 일부가 모듈 B에 포함되어 있습니다. 이로 인해 모듈 A의 코드를 수정하기 위해서 모듈 B를 건드려야 하고 모듈 B를 건드리다 보면 이를 사용하는 다른 코드까지 문제가 전이됨으로 인해 의도치 않은 문제들을 야기할 수 있습니다. 이처럼 단일 모듈이 스스로 완성되지 못하고 다른 모듈에 의존하게 되는 것을 '응집도가 낮다'라고 말합니다.
나쁜 설계는 또한 모듈 간의 높은 결합도를 가지고 있습니다. 예를 들어, 결제 모듈에서 Paypal 모듈을 사용하다가 네이버페이로 변경하고 싶은 상황입니다. 그런데 결제 모듈 내부에서 Paypal 모듈을 직접 가져와서 사용하다 보니 코드를 분리하게 되면 결제 모듈이 완전히 박살이나 재사용할 수 없는 지경이 되니, 차라리 네이버페이를 사용하는 결제 모듈을 새로 만드는 것이 나아 보입니다. 이처럼 모듈이 서로 강하게 결합되어 있어서 쉽게 떼어낼 수 없는 것을 '상호 결합도가 높다'라고 합니다.
좋은 설계
좋은 설계는 나쁜 설계 요소가 없는 설계, 즉 '상호 결합도가 낮고 응집도가 높다'라고 말할 수 있는 설계입니다.
상호 결합도가 낮고 응집도가 높으면 다음과 같은 이점이 있습니다.
- 낮은 결합도로 인해 모듈을 쉽게 분리할 수 있고 다른 곳에서도 재사용하기 수월합니다.
- 응집도가 높으므로 일부를 변경하더라도 다른 모듈에 문제가 전이되지 않아 유지보수가 수월합니다.
좋은 설계가 무엇인지는 감을 잡았지만, 어떻게 좋은 설계를 할 수 있을까요? 그 가이드 역할을 하는 것이 바로 SOLID 원칙입니다.
🐭 그런데 Go는 객체지향 언어가 아니잖아요?
Go는 엄밀히 따지면 그 설계부터 간결하고 효율적인 코드를 지향하므로 객체지향 언어 프로그래밍과는 거리가 있습니다. 여타 객체지향 언어가 가지고 있는 'class', 'implements', 'abstract' 등의 키워드가 존재하지 않으니까요.
그렇다면 Go에는 SOLID 원칙을 적용할 수 없을까요? 그렇지 않습니다!
SOLID는 객체 지향 언어에 국한되어 있지 않고 소프트웨어 디자인 전반적으로 적용이 가능한 가이드로써 활용할 수 있습니다. 그리고 Go가 객체 지향과 완전히 대척점에 서있는 것도 아닙니다. Go는 메서드, 인터페이스, 구조체 임베딩 등을 활용하여 객체 지향 언어가 가진 특징들을 표현할 수 있습니다. 따라서 Go도 SOLID를 적용한 좋은 설계가 가능합니다.
🙏 마치며
SOLID 원칙과 좋은 설계가 무엇인지 그리고 Go가 객체지향 언어가 아님에도 SOLID를 적용할 수 있는지에 대해 알아보았습니다. 다음 게시물에서는 Go의 객체 지향적인 면모들을 살펴보고 SOLID 각각의 원칙들에 대해 하나씩 짚어보겠습니다.
글에서 수정이 필요한 부분이나 설명이 부족한 부분이 있다면 댓글로 남겨주세요!
'Go > 디자인 패턴' 카테고리의 다른 글
[Go] SOLID in Go - 단일 책임 원칙 (1) | 2023.10.11 |
---|---|
[Go] SOLID in Go - 패키지 (1) | 2023.10.10 |
[Go] SOLID in Go - 컴포지션 (1) | 2023.10.09 |
[Go] SOLID in Go - 인터페이스 (1) | 2023.10.04 |
[Go] SOLID in Go - 구조체와 메서드 (0) | 2023.10.03 |