- "로버트 c.마틴"의 <클린 아키텍처>를 읽고...
이 글은, "로버트 c. 마틴" 의 <Clean Architecture> 이라는 원서를 읽고 작성하는 서평입니다. 보통 서평이란 책을 읽고, 간단하게 요약하고 평가를 하는 것으로 책 내용의 일부분만 서평에 포함할 수 있습니다. 그래서 책의 많은 내용 중에서 제가 가장 생각을 많이 했던 문구를 간단하게 정리해서 글로 남깁니다. 솔직한 마음으로는, 이 좋은 책을 전부 번역해서 글로 남기고 싶지만, 아마도 어느 출판사에서 <Clean Architecture>를 번역 하고 있으리라 생각합니다. 제가 원서에 대한 저작권이 없는 상황에서 정식 번역책이 나오지 않은 상황에서 원서의 모든 내용을 글로 남기는 것은 옳지 않다고 생각하여... 매우 아쉽지만 간단하게 서평으로 기록을 남깁니다. 조만간 번역서가 나오는거 맞겠지요? 사실 번역서가 조금 늦게 출판되는 것은 상관없습니다. 대신, 이 좋은 책을 읽기 쉽게 제대로 번역이 되었으면 좋겠습니다. 출판사의 번역본이 이상하다면 매우 실망할 것입니다.
훌륭한 소프트웨어 아키텍트(개발자)는 미래를 예측할 수 있어야 한다. 소프트웨어 운영 비용을 평가하고 구조적인 경계가 어디에 있는지, 어떤 것이 구현되어야 하는지, 어떤 것이 무시되어야 하는지 결정할 수 있어야 한다. 그런 결정은 일회성 결정이 아니다. 즉, 시작부터 결정하는 것이 아니라, 소프트웨어가 발전할 때마다 주의 깊게 검토를 해야 한다.
개발 조직은 소프트웨어 아키텍처의 품질을 심각하게 받아들이기 시작해야 한다. 좋은 소프트웨어 아키텍처가 무엇인지 알아야 하고, 노력을 최소화하면서 생산성을 극대화하는 설계에 대해서 알아야 한다. 소프트웨어가 당장 멋지게 작동하는 것보다, 소프트웨어를 쉽게 변경할 수 있도록 만드는 것이 더 중요하다. 완벽하게 작동하지만 변경할 수 없는 소프트웨어를 만들면, 요구사항이 변경될 때 제대로 작동하지 않을 수 있다. 반면에, 당장 작동하지는 않지만, 변경하기 쉬운 프로그램을 만들면 요구사항의 변화에 지속적으로 작동하게 할 수 있다. 그러므로, 소프트웨어는 지속적으로 유용할 것이다. 쉽게 수정하고, 쉽게 확장할 수 있는 아키텍처를 만들어야 하고, 그것은 바로 개발자의 책임이다.
좋은 아키텍처는 특정 프레임워크, 도구, 환경에 상관없이 유스케이스(비즈니스 로직)에 집중해야 한다. 그 집이 벽돌로 만들어졌는지 확인하는 것이 아니라, 그 집이 사용 가능한지 먼저 확인하는 것이 훨씬 더 중요하다. 유스케이스, 즉 사용 사례가 충족되는지 확인한 후, 벽돌로 할지, 석재로 할지 결정을 할 수 있어야 한다. 훌륭한 소프트웨어 아키텍처는 프레임워크, 데이터베이스, 웹서버 등 기타 환경 문제와 도구에 대한 결정을 미룰 수 있어야 한다.
소프트웨어 아키텍처는 경계라는 선을 그리는 예술이다. 이러한 경계들은 소프트웨어 요소들을 서로 분리하고 디펜던시 의존성을 제한한다. 아키텍트의 목표는 필요한 시스템을 구축하고 유지하는 데 필요한 인적 리소스를 최소화하는 것이다. 예를 들어서, 비즈니스 유스케이스와 데이터베이스 사이의 경계선을 그릴 수 있다. 그 선은 비즈니스 규칙이 데이터베이스에 대해 전혀 알지 못하도록 막았다. 그 결정은 데이터베이스의 선택과 실행을 뒤로 늦출 수 있었고, 데이터베이스에 의존한 문제가 발생하지 않았다. 중요한 것과 중요하지 않은 것 사이에 선을 긋는다. UI는 비즈니스 규칙에 영향을 미치지 않아야 하고, 데이터베이스는 UI에 영향을 미치지 않아야 한다. 물론, 대부분의 우리들은 데이터베이스는 비즈니스 규칙과 불가피하게 연결되어 있다고 믿고 있다. 하지만, 데이터베이스는 비즈니스 규칙이 간접적으로 사용할 수 있는 도구일 뿐이다. 그래서, 우리는 인터페이스 뒤에 데이터베이스를 놓을 수 있도록 설계를 해야 한다. 실제로 소프트웨어 개발, 기술의 역사는 확장 가능하고 유지 관리 가능한 시스템 아키텍처를 구축하기 위해 플러그인을 만드는 방법에 관한 이야기이다. 핵심 비즈니스 규칙은 다른 컴포넌트들과 독립적으로 유지된다.
프레임워크는 매우 강력하고 유용할 수 있다. 프레임워크를 만든 사람들은 보통 그들의 프레임워크를 매우 깊게 믿는다. 모든 것을 포함하고, 모든 것을 할 수 있는 것을 만들려고 한다. 또한, 그 프레임워크를 너무 믿는 경향이 있다. 하지만,
Ask yourself how you should use it, and how you should protect yourself from it.
무조건 맹신해서는 안되며, 프레임워크에 대해서 항상 객관적인 시선으로 지켜봐야 한다. 프레임워크의 구조는 종종 깨끗하지 않다. 때로는 종속성 규칙을 위반하는 경향이 있다. 그들은, 즉 프레임워크 창시자는 그들의 코드를 우리의 비즈니스 객체, 우리의 엔티티로 상속해 달라고 요청한다. 한번 결합한 프레임워크라는 틀에서 다시 나오기 쉽지가 않다. 프레임워크로부터 아키텍처의 유스케이스를 보존할 수 있는 방법을 항상 생각해야 한다. 가능한 오랫동안 구조적 경계 뒤에 프레임워크를 뒤에 유지하자. 프레임워크는 유용하지만, 모든 것을 해결해주는 만능 도구는 아니라는 점을 항상 명심해야 한다.
<클린 아키텍처> 의 동심원은 소프트웨어의 각각 다른 레이어 영역을 나타낸다. 내부 원은 비즈니스 정책이다. 클린 아키텍처에서 가장 중요한 개념은 디펜던시(의존성) 규칙이다. 소스 코드 의존성은 내부에서만 상위 수준 정책을 가리키도록 해야 한다. 내부 원 안에 있는 어떤 것도 외부 원의 무언가에 대해서 전혀 알 수 없다. 외부 원에 있는 어떤 것도 내부 원들에 영향을 미치기를 원하지 않는다. Entities는 전사적으로 중요한 비즈니스 규칙을 요약한다. Entities 는 메서드를 포함하는 객체일 수도 있고, 데이터 구조일 수도 있다. Entities 는 가장 일반적이고 높은 수준의 규칙을 요약한다. 외부적인 무언가가 바뀌면 가장 덜 변해야 한다. UseCase는 애플리케이션별 비즈니스 규칙을 포함한다. 시스템의 모든 사용 사례를 캡슐화하고 구현한다. 이러한 사용 사례는 기업 간 데이터 흐름을 조정한다. UseCase 계층은 데이터베이스, UI 또는 어떤 공통 프레임워크 등 외부에 영향을 받을 것으로 기대하지 않으며, 외부 영역으로부터 격리되어야 한다. InterFace Adapter 계층은 컨트롤러와, 모델, 뷰 등 MVC 아키텍처를 포함하는 계층이다. 마지막으로 가장 바깥쪽 계층인, Framework & Drivers 영역은 일반적으로 데이터베이스 및 웹 프레임워크와 같은 도구로 구성된다. 사실, 이 네 개 영역 이상의 것이 필요할 수 있다. 그러나, 디펜던시 규칙은 항상 적용이 된다. 소스 디펜던시는 항상 안쪽을 가리키며, 내부로 이동함에 따라 추상화 수준이 높아진다. 이러한 규칙을 준수하는 것은 어렵지 않으며, 앞으로 많은 고민들을 해결해 줄 것이다. 소프트웨어를 계층으로 분리하고, 디펜던시 규칙을 준수함으로써, 데이터베이스나 웹 프레임워크와 같은 시스템이 외부 부분들이 쓸모없게 될 때, 그러한 쓸모없는 요소들을 최소한의 작업으로 대체할 수 있을 것이다.
"로버트 c.마틴"의 조언은 잘 정의된 경계, 명확한 책임 및 통제된 의존성으로 더 나은 소프트웨어를 설계하는 데 확실히 도움이 될 것이다. 하지만, 실제로 구현 세부 사항에서는 악마(?)가 있다는 것을 깨닫게 된다. 이것을 생각하지 않는다면 마지막 장애물에 빠지기 쉽다. <클린 아키텍처> 를 잠시 넣어두고, 다양한 설계 디자인에 대해서 다양하게 접근을 해서 검토해야 한다. <클린 아키텍처> 가 최고의 설계 의도일 수 있지만, 구현 전략의 복잡함을 고려하지 않는다면, 좋은 소프트웨어를 유지하겠다는 의도는 한순간에 파괴될 수 있다. 원하는 설계를 코드 구조에 매핑하는 방법, 해당 코드를 구성하는 방법, 런타임과 컴파일 시간에 적용할 디커플링 모드에 대해서 심각하게 검토해봐야 한다. 또한, 적용 가능한 옵션을 열어두 고고, 팀의 규모와 기술 수준, 일정을 고려해서 소프트웨어의 복잡성을 고려해야 한다.
"로버트 c. 마틴"은, 아마도 전 세계에서 가장 영향력 있는 아키텍트 중 한명일 것이다. 그동안 필자는, 필자의 서재 책장에 가장 잘 보이는 위치에 꽂혀있는 <클린 코드>, <클린 소프트웨어> 두 권의 번역서를 통해서 많은 도움을 받았었다. 평범한 프로그래머이면서, 좋은 아키텍트가 되고 싶은 필자에게 <클린 아키텍처> 는 그동안 필자가 개발자로 살아오면서 느꼈던 소프트웨어 개발의 가치에 대해서 다시 한번 생각하게 해주는 좋은 원서라고 생각한다. 비록, 필자의 부족한 영어 실력으로 "로버트 C.마틴" 의 생각이 100% 필자에게 전달이 되지는 않았고, 로버트 c.마틴의 이론이 다소 추상적인 개념으로, 실제 구현 사례에 대한 예시가 부족하여, 현실 세계에서 바로 적용하기 쉽지는 않다고 생각한다. 그럼에도 불구하고, 이 책은 필자가 소프트웨어를 잘 만들고 싶고, 잘 유지하고 싶다는 소중한 가치를 깨닫게 해주고, 그 책임이 바로 나 스스로에 있다는 사실을 다시한번 깨닫게 해주는 소중한 책이다. 비록, 현실은 생각처럼 쉽지 않고, 소프트웨어는 사람의 욕심으로 인해서 필연적으로 복잡해질 수밖에 없다는 사실을 잘 알고 있지만, 그것을 풀어갈 수 있는 유일한 길은, 개발자의 책임감과 소프트웨어를 지혜롭게 유지할 수 있도록 클린 아키텍처를 잘 설계하고 유지해 가는 방법뿐이라고 생각한다. 소프트웨어를 방치하고 떠난 퇴사자를 원망하지 말자. 설계문서가 없다고 원망하지 말자. 무분별하게 요구사항을 요청하는 기획팀을 원망하지 말자. 늦었다고 생각하지 말고, 지금부터라도 가치 있는 일을 찾아서 하나씩 차분하게 진행하면 될 것이다. 그것이 바로 개발자의 몫이고, 필자의 책임이라고 생각한다. 그동안, 방치되고 관리되지 않은 수많은 소프트웨어를 리팩터링 하고 개선하면서 생각했던 필자의 가치들이, <클린 아키텍처> 를 통해서 조금이나마 위안이 되었다는 사실에 "로버트 c.마틴" 에게 진심으로 감사하게 생각한다.
가장 인상 깊었던 문구를 마지막으로 이 서평을 마치겠다.
"로버트 c.마틴"의 <클린 아키텍처>의 번역서가 나오기를 간절히 기대하고 있습니다.
내용 추가
1. 클린 아키텍처 번역본이 최근에 출간 되었습니다.
2. 클린 아키텍처를 적용해서 아키텍처를 검토한 글입니다.
https://brunch.co.kr/@springboot/228