Eileen은 대규모 Rails 애플리케이션이 겪는 고통점을 아키텍처, 운영, 조직적 문제로 분류하고, 모듈형 모놀리스가 이러한 문제를 해결하는 데 실패하는 이유를 설명합니다.
1. 대규모 Rails 애플리케이션의 고통점
- 아키텍처 문제:
- 조직 및 구조 부족: Rails의 기본 MVC 구조만으로는 방대한 코드베이스를 관리하기 어려워 ‘진흙 덩어리(ball of mud)’가 됩니다. 코드의 위치와 리팩토링 우선순위가 명확하지 않아 개념들이 뒤섞입니다.
- 강한 결합 및 경계 부족: Ruby의 전역 접근성으로 인해 코드 간 강한 결합이 쉽게 발생하며, 이는 예측 불가능한 영향과 개발 생산성 저하를 초래합니다.
- 운영 문제:
- 느린 CI 및 불안정한 테스트: 모놀리스 규모가 커질수록 불안정한 테스트(flaky tests)가 빈번해지고 CI 속도가 저하됩니다. 이는 네트워크 호출, 과도한 레코드 생성, 전역 상태 오염 등 다양한 기술 부채에 기인합니다.
- 배포 확장성 어려움: 애플리케이션 규모 증가 시 배포 시간이 길어지고, 특정 부분만 독립적으로 확장 배포하기 어렵습니다.
- 조직 문제:
- 오너십 할당 및 신규 채용 온보딩 어려움: 수천 명의 엔지니어 규모에서 코드 오너십이 불분명하고, 거대한 코드베이스는 신규 개발자에게 큰 진입 장벽이 됩니다.
- “전체 애플리케이션을 머리에 담을 수 없다”는 주장의 반박: 이는 개인적인 문제이며, 애플리케이션 크기를 판단하는 유효한 기준이 아닙니다. 중요한 것은 잘 설계된 구조와 Rails 컨벤션 준수입니다.
2. 모듈형 모놀리스의 약속과 현실
모듈형 모놀리스는 마이크로서비스의 격리성과 모놀리스의 개발 편의성을 결합하는 이상적인 해결책으로 제시됩니다. Rails Engines와 Packwerk Gem을 사용하여 모듈 간 경계를 정의하고 강제하는 방식이 사용됩니다. 그러나 Eileen은 다음과 같은 문제점들을 지적합니다.
-
진정한 격리의 어려움: Packwerk는 의존성을 식별하지만, 기존 코드 리팩토링 없이는 결합도 감소나 경계 도입이 어렵습니다. Shopify조차 완전 격리된 모듈을 프로덕션에 배포하지 못하고 있습니다.
-
안티패턴 유발:
- 원시 타입 집착(Primitive Obsession): 의존성 위반을 피하기 위해 Active Record 객체 대신 ID를 전달하고 재쿼리하는 패턴으로 인해 데이터베이스 성능 저하와 데이터 중복이 발생합니다.
- 오너십 집착(Ownership Obsession): 패키지 내 코드가 특정 팀의 전유물이라는 사고방식은 사일로를 만들고 협업을 저해하며 코드 품질을 희생시킵니다.
- 패키지 집착(Package Obsession) 및 코드 중복: 모든 새로운 개념을 별도 패키지로 만들거나 의존성 회피를 위해 코드를 복사하는 관행은 코드베이스를 파편화하고 비대하게 만들며 유지보수를 어렵게 합니다.
- 순환 의존성(Circular Dependencies): 대규모 애플리케이션에서 순환 의존성 해결 및 방지는 매우 어려우며, 이를 회피하려다 성능 저하를 초래하기도 합니다.
3. 근본 원인: 인간적, 문화적 문제
Eileen은 이러한 문제들이 코드베이스를 이동하거나 아키텍처를 변경하는 것만으로는 해결되지 않는다고 강조합니다.
-
문제의 본질: 도구는 문제점을 알려줄 뿐, 더 나은 조직화, 설계, 기술 부채 해결은 개발자의 이해와 교육, 그리고 리더십의 우선순위 설정이 필요합니다.
-
조직 문화의 영향: 오너십, 온보딩, 책임감 부족 등은 리더십과 회사 문화에 깊이 뿌리내린 문제입니다. 기능 출시 우선주의, 기술 부채 무시, 책임 전가 문화 등 잘못된 인센티브 구조가 문제의 핵심입니다. 아키텍처는 이러한 문화적 문제를 해결할 수 없습니다.