마이크로서비스 아키텍처 (크리스 리차드슨)

This a translation of an article Microservices Architecture originally written and copyrighted by Chris Richardson.
이글은 Chris Richardson가 작성하였으며, 저작권을 가지고 있는 Microservices Architecture 글의 번역본입니다.

맥락 (Context)

서버 사이드 기업용 애플리케이션 개발을 하고 있다고 해보자. 데스크탑 브라우저와 모바일 브라우저, 그리고 네이티브 모바일 애플리케이션을 포함해 여러 가지 다양한 클라이언트 지원해야만 한다. 또한, 애플리케이션은 3rd 파티가 사용할 수 있도록 API를 노출해야 할 수도 있다. 또한 웹서비스나 메시지 브로커를 통해서 다른 애플리케이션 서비스와 통합해야 할 수도 있다. 애플리케이션은 비즈니스 로직을 실행하고, 데이터베이스에 접근하며, 다른 시스템들과 메시지를 주고받아 HTML/JSON/XML 응답을 돌려주는 것으로 요청(HTTP 요청과 메시지)을 처리한다

애플리케이션은 계층형 아키텍처나 6방형(hexagonal) 아키텍처를 갖거나 다양한 유형의 컴포넌트로 구성되어 있다.

이들은 애플리케이션의 다양한 기능적인 측면에 상응하는 논리적인 컴포넌트이다.

문제 (Problem)

애플리케이션의 배포 아키텍처는 어떤 것인가?

영향도 (Forces)

해결방법 (Solution)

Scale Cube(특히 Y-축 스케일 확보)를 적용해 애플리케이션 아키텍처를 수립하고, 기능적으로 애플리케이션을 서비스 조합의 집합으로 분해한다. 각 서비스는 제한적으로 관련된 기능의 집합을 구현한다. 예를 들어, 하나의 애플리케이션은 주문 관리 서비스, 고객 관리 서비스 등과 같은 서비스로 구성할 수 있다.

서비스는 HTTP/REST와 같은 동기방식 프로토콜을 사용하거나 AMQP와 같은 비동기 방식 프로토콜을 사용해 상호소통을 한다.

서비스는 서로 간에 독립적으로 개발되고 배포된다.

각 서비스는 다른 서비스와 분리하기 위해서 자신의 데이터베이스를 갖는다. 필요할 때 데이터베이스 간의 일관성은 데이터베이스 복제 매카니즘이나 애플리케이션 수준의 이벤트를 사용해 관리한다.

예시

고객에서 주문까지, 재고(inventory)를 확인하고, 신용결재(credit)가 가능하며, 이를 출하(ships)할 수 있는 전자 상거래 애플리케이션을 구축한다고 상상해보자. 애플리케이션은 신용거래를 확인하고, 재고를 관리하고, 주문을 출하하는 백 엔드 서비스와 함께 사용자 인터페이스를 구현하는 StoreFrontUI를 포함하는 각각 컴포넌트로 구성한다.

애플리케이션은 서비스 집합으로 배포한다.

app

상황 해결하기

이 해결방법에는 여러 장점이 있다.

이 해결책은 다음과 같은 단점이 있다.

이 접근 방법을 사용하려고 할 때 겪는 첫 번째 도전은 이 방법을 사용하기에 적절한지에 따라 판가름이 난다. 애플리케이션의 첫 번째 버전을 개발하는 시기에는 이 접근 방법이 해결해 주는 문제를 대부분 겪고 있지 않을 것이다. 게다가 분산 아키텍처를 정교하게 사용할수록 개발 속도가 늦어진다. 이 점이 시작할 때 가장 큰 문제가 되며, 대부분 빠르게 발전하는 비즈니스 모델에 맞춰서 얼마나 애플리케이션을 만들어 가는 지가 가장 큰 도전 과제다. Y 축을 사용해 빠르게 반복하는 것이 더 어렵다고 할 수 있다. 그렇지만 향후에 도전 과제가 어떻게 스케일을 확보하고 기능 분해를 사용할 필요해 지면, 엉망이 된 의존성은 모놀리틱 애플리케이션을 서비스의 집합으로 분해하는 것이 더 어려울 것이다.

또 다른 도전 과제는 어떻게 시스템을 마이크로서비스로 분할(partition)할 건지 결정하는 것이다. 이건 매우 예술적인 일이지만 도움이 되는 몇 가지 전략이 있다. 첫 번째 방법은 동사와 유즈 케이스로 서비스를 분할하는 것이다. 예를 들어, 향후 분할된 전자 상거래 애플리케이션은 출하 완료 주문에 대한 책임을 출하 서비스(Shipping service)가 갖는 것을 생각해 볼 수 있다. 또 다른 동사로 분할한 흔한 예로 로그인 유즈 케이스를 구현한 로그인 서비스를 들 수 있다.

또 다른 분할 접근 방법은 명사와 리소스로 시스템을 분할하는 방법이다. 이러한 서비스의 유형은 해당 타입의 엔티티/리소스의 모든 연산에 대한 책임을 진다. 예를 들어, 향후 상품 재고가 있는지 추적하는 재고 서비스(Inventory service)를 제공하는 전자 상거래 시스템의 의미를 생각해 볼 수 있다.

이상적으로는 각 서비스가 작은 책임의 집합으로만 되어 있어야 한다. (Uncle Bob이라 불리는) 밥 마틴은 단일 책임 원칙(SRP, Single Responsible Principle)을 사용해 클래스를 설계하라고 얘기한다. SRP는 변경의 이유에 따라서 클래스의 책임을 정의하며, 이 때 클래스에는 반드시 변경 원인이 하나만 있어야 한다. 서비스 설계 시에 SRP 또한 적용해보는 것 또한 의미가 있다.

또 다른 서비스 설계에 도움이 되는 유사점은 유닉스(Unix) 유틸리티 설계에서 볼 수 있다. 유닉스는 grep, cat, find와 같은 매우 많은 수의 유틸리티를 제공한다. 각 유틸리티는 정확히 하나이며, 종종 복잡한 작업을 수행하기 위해 특별히 쉘 스크립트를 사용해 다른 유틸리티와 잘 조합될 수 있다.

관련 패턴

모놀리틱 아키텍처와 대체 가능한 패턴이다.

쓰임새

Netflix, Amazon, eBay를 포함해 대부분 대규모 웹 사이트는 모놀리틱 아키텍처에서 마이크로서비스 아키텍처로 발전해 왔다.

인터넷 트랙픽의 30%까지 책임지는 가장 유명한 비디오 스트리밍 서비스 회사인 Netflix는 대규모 서비스 지향 아키텍처(service-oriented architecture)이다. 이들은 비디오 스트리밍 API로 매일 800개가 넘는 디바이스에서 오는 백만 번 이상의 호출을 처리한다. 각 API 호출은 평균적으로 백 엔드 서비스의 6번 호출로 전개된다.

Amazon.com은 본래부터 2-티어 아키텍처였다. 스케일 확보를 위해 수백 개의 백 엔드 서비스로 구성되는 서비스 지향 아키텍처로 이동했다. 몇몇 애플리케이션은 Amazon.com 웹사이트와 웹서비스 API를 구현하는 애플리케이션에 들어가 있는 서비스를 호출한다. Amazon.com 웹 사이트 애플리케이션은 웹 페이지를 구성하는 데 사용하는 데이터를 얻기 위해 100~150개 서비스를 호출한다.

경매 사이트인 ebay.com 역시 모놀리틱 아키텍처에서 서비스 지향 아키텍처로 발전해나갔다. 애플리케이션 티어는 다수의 독립적인 애플리케이션으로 구성되어 있다. 각 애플리케이션은 구매나 판매처럼 특정 기능 영역에 대한 비즈니스 로직을 구현한다. 각 애플리케이션은 X-축 분해를 사용하고, 검색과 같은 일부 애플리케이션은 Z-축 분해를 사용한다. 또한, ebay.com은 X-, Y-, Z- 스타일의 스케일 확보 방법을 조합해 적용했다.