[MSA] 마이크로서비스 Frontend 통합 방안
마이크로서비스를 Web Frontend와 통합하는 방법을 알아보려고 한다.
1. Frontend 구현 아키텍쳐
1.1 모놀리틱 Frontend + 모놀리틱 Backend
전통적인 웹 개발 방법으로 시스템이 너무 작거나 간단한 경우 모듈화는 하는 것 자체가 많은 노력이 필요하기 때문에, 이 경우 불피요한 모듈화 작업을 수행하지 않음으로써 이에 들어가는 에포트를 줄일 수 있다.
1.2 모듈화된 모놀리틱 Frontend + 마이크로서비스 Backend
모놀리틱으로 배포되는 frontend도 모듈화되어서 개발될 수 있다. 이 경우 모듈 단위로 개발할 수 있지만 결국 배포는 전체 frontend 단위로 수행되기 때문에 microservice가 갖는 배포 관점의 장점을 가질 수 없다.
경험적으로 이러한 시스템은 시간이 지남에 따라서 유지관리하기 어려워지고, 점차 모듈화 되지 않는 시스템으로 변할 수 있다. 이런 구조는 계속 시스템을 수정해가면서 모듈간의 경계가 허물어져갈 수 있다.
모놀리틱으로 Frontend를 구현하는 이유
아래와 같은 상황에서는 frontend를 모놀리틱으로 구현하는게 적합하다.
- Native mobile & client app : 모바일 앱 같은 경우 앱 스토어에 업데이트 하기전에 제대로 개발되었는지 앱을 리뷰하는 절차가 있다. 따라서 배포는 항상 오래걸리고 모놀리틱으로 배포되어야 할 수 있다. 만약에 앱 안에서 웹을 사용하는 경우(ex. Cordova 프레임워크 사용) 웹의 기능은 마이크로서비스로 구축될 수 있기 때문에, 다운받은 앱에서 마이크로서비스와 결합하여 제공할 수 있다.
- SPA(Single page App)s : SPA는 항상 하나로 배포가 된다. 만약 모듈화를 하기 위해서는 별도의 대안책을 사용해야 한다. SPA는 다른 사이트나 다른 SPA 그리고 다른 시스템에서 생성한 HTML을 제공하여 유연하게 사용할 수 있다. 이러한 이론적인 방식으로 SPA를 frontend에 통합할 수 있으나, 일반적으로 SPA는 모놀리틱 frontend로 배포를 한다.
- Single team : 만약 하나의 팀만 frontend 개발에 할당이 되었다면 굳이 microservic로 frontend를 구현하는 것 보다 모놀리틱 frontend로 개발하는 것이 나을 수 있다.
- Migration : 기존에 사용하고 있는 모놀로틱 frontend가 남아있다면 기존과 동일하게 모놀리틱 frontend로 사용하는 것이 쉽다.
1.3 마이크로서비스 Backend 내 모듈화된 Frontend
모놀리틱 frontend의 대안으로 완전한 모듈화를 이야기할 수 있다. 모듈화된 frontend가 각 microservice에서 동작하게 된다. Backend와 동일하게 frontend도 microservice 단위로 배포될 수 있다.
모듈화된 frontend의 장점
- microservice 또는 SCS는 도메인 로직과 독립적으로 구성할 수 있다.
- 만약 microservice 아래에 모듈화된 frontend가 있다면 도메인의 변경이 독립적으로 하나의 microservice에 대해서만 수행된다. (backend/frontend 상관 없이)
- 모놀로틱 UI를 사용한다고 하면, 어떤 microservice가 담당하는 도메인이던 간에 항상 변화가 발생할 수 있다. 따라서 frontend는 모든 변경에 대해서 수정되어야 되며, 개발이 집중된다.
모듈화된 Frontend 통합
모듈화되어 microservice에 올라간 frontend는 개별적으로 배포될 수 있지만, 하나의 완전한 시스템을 위해서는 frontend는 통합되어야 한다. 모듈화 자체는 개발에 대한 결합성을 낮추기 위해서 사용된다. 하지만 실제로 서비스를 제공하기 위해서는 각 microservice에 있는 frontend들은 모두 통합된 형태로 제공되어야 한다. 이것을 통합하기 위한 다양한 기술적 방법이 존재한다.
2. Frontend 통합 방안
앞서 모듈화된 frontend를 통합하기 위한 방안을 이야기해 보자
2.1 Link를 통한 연결
가장 쉬운 방법으로 하나의 frontend에서 다른 frontend를 다루기 위한 링크를 걸어주는 것이다. ‘WWW’ 기반에서 이러한 방식은 정확하게 동작하며, 하나의 시스템이 다른 하나의 시스템을 가리키는 것으로 구현한다.
2. 2 Redirect를 통한 연결
Redirect는 다른 대안으로 사용할 수 있다. 예를들어 OAuth2를 사용하는 경우 다음과 같이 접근할 수 있다. 이 방식은 frontend 통합과 backend의 데이터 전송과 통합시킬 수 있다.
- 웹 사이트에서 Oauth2 제공자 (facebook, google 등)에 대한 링크를 제공한다
- 사용자는 계정정보를 통해 웹사이트에 대한 특정 정보 접근을 승인받는다
- 사용자는 그 후에 또 다른 redirect를 통해 원래 웹사이트로 돌아온다. 이전 사이트로부터 사용자 인증 정보를 전달받아 사용한다.
2.3 Transclusions
이 방식은 다른 웹사이트의 내용을 포함시키는 방법이다. 이것은 server/client 모두에서 수행될 수 있다. 이 방법은 다른 방법과 조합될 수 있지만 기술적으로 복잡도가 증가한다. 그렇기 때문에 가장 먼저 위의 link와 redirect 방식을 통해 접근하는 것을 권장한다. (자세한 내용은 뒤에 더 설명하겠다.)
3. ROCA, Resource-Oriented Client Architecture
Frontend에서의 모듈화와 통합은 아키텍쳐와 사용하는 기술들에 대해서 영향을 끼친다. 예를들어 SPA는 frontend 통합에는 적합하지 않다. 따라서 어떠한 아키텍쳐가 frontend 통합에 더 적합한지 궁금할 수 있다.
**ROCA(Resource-Oriendted Client Architecture)**는 web app을 구현을 위해 권장되는 구현 방법이다. 이것은 HTML과 같은 web 기술들에 중점을 두고 있으며, frontend 모듈화 및 통합에 많은 이점을 구성하는 아키텍쳐를 만들 수 있는 방식이다.
3.1 ROCA 원칙
ROCA를 구현하기 위한 몇가지 원칙이 존재한다.
- REST 원칙 : 서버는 REST 원칙을 고수해야 한다.
- 모든 자원들은 명확한 URL을 가지고 있어야 한다
- 만약 필요한 권한이 있다면, 어떠한 웹 브라우저에서든 웹 페이지를 접근할 수 있어야 한다.
- HTTP 메소드가 올바르게 동작해야 한다. 예를들어, GET은 데이터 교환에 사용되면 안된다.
- 서버는 stateless 여야 한다.
- 접근 가능한 정보: 모든 리소스는 URL을 통해서 식별될 수 있어야 하며, 다른 방식(HTML, JSON, XML 등)으로 표현될 수 있어야 한다. 이것은 단순히 데이터가 사람에 의해서 사용되는 것이 아니라 application에 의해서 사용될 수 있다는 것을 의미한다.
- 모든 로직은 server에 있어야 한다 : 모든 로직은 서버(backend)에서 수행되어야 하며, JavaScript와 같은 frontend는 UI를 최적화 하는 역할만 수행한다. 보안적인 측면에서도 client가 데이터를 수정할 수 있기 때문에 서버에 로직이 있는것이 바람직하다. 또한 로직의 변경이 필요한 경우에도 수 많은 client를 수정하지 않아도 되기 때문에 서버에서 구현하는 것이 좋다.
- HTTP 요청을 통한 인증 : 인증정보는 HTTP 요청에 포함되어야 한다. HTTP 인증(basic /digest), client 인증서, 쿠키가 이러한 역할에 사용된다. 이 방법을 사용하면, 모든 인증/권한 정보가 HTTP에 포함됨으로, 서버에 대한 세션이 필요없다.
- 쿠키Coockes 사용 : 쿠키는 다음과 같이 사용될 수 있다.
- 인증
- 트랙킹Tracking
- 사이트 간 요청 위조 방지
- Server-side 세션이 없어야 함 : 반드시 어떠한 서버 세션이 없어야 한다. 서버의 사용은 HTTP 본래 의도에 어긋난다. 그렇기 때문에 통신은 stateless로 수행되어야 한다. 이러한 상태는 failover나 load-balancing을 어렵게 한다. 세션을 사용해도 되는 예외는 HTTP 요청으로 인한 인증 외에 다른 추가적인 인증이 필요할 경우이다. (뱅킹 서비스 등)
- Browser 제어 : 뒤로가기, 앞으로가기, 새로고침과 같은 브라우저 제어 기능이 동작해야 한다. 이것은 기본적인 것이지만 많은 web app이 JavaScript 로직으로 이러한 기능을 제공하는 것이 어렵고 또 이것을 제공하기 위해 많은 작업들을 수행해야 한다.
- HTML에 레이아웃 정보가 없어야 함 : 레이아웃은 CSS에 의해서 정의되어야 하고 페이지의 컨텐츠는 분리가 되어야 한다.
- JavaScript는 추가적으로 사용 : JavaScript 는 점진적 향상을 위해서 사용하고, app은 기본적으로 JavaScript 없이 동작할 수 있게 한다. 목표는 JavaScript를 사용하지 않는 것이 아니라 아키텍쳐 기반을 web 기술 - HTTP, HTML, CSS 에 두는 것이다.
- 중복된 로직이 없어야함 : Client와 Server가 중복된 로직을 가지고 있으면 안된다. 다시 이야기하면, 도메인 로직은 client에서 가지고 있으면 안된다.
위의 원칙들을 보건데.. ROCA는 일반적으로 완벽한 web app을 의미한다. ROCA에서 이야기하는 원칙은 web에 대한 이상적인 원칙이기도 하다.
3.2 ROCA 장점
ROCA는 몇가지 장점을 가지고 있다.
- 아키텍쳐가 깔끔해진다. 로직은 서버에서 구현되고, 로직에 대한 변경사항은 쉽게 새로운 서버 버전으로 rolled-out 될 수 있다.
- 웹 기능에 제약이 생기지 않는다. URL은 공유될 수 있으며, 자체적으로 cache를 사용하고 브라우저 기반으로 동작한다.
- 낮은 대역폭이 요구된다. 실제로 방문하는 페이지의 리소스만 가져옴으로 낮은 대역폭을 사용하게 된다. 반면에 SPA 같은 경우 전체 app에 대한 데이터가 먼저 전송되어야 한다. 최신의 SPA 기술은 전체를 가져오는 것이 아닌 모듈화를 할 수 있지만 초반 설정 시간은 여전히 오래걸린다.
- 속도가 빨라진다. JavaScript를 적게 사용함으로 빠르게 처리된다. 모바일 장치에 적합하다.
- 복구가 가능해진다. JavaScript 레벨의 에러나 전송 에러는 복구하기 어려우나, 서버로 로직을 가져옴으로써 시스템은 복구하는데 더 용이하다.
3.3 ROCA와 SPA 비교
- ROCA는 웹 기반 기술 (HTML, HTTP)을 위해 브라우저 최적화 기능을 사용할 수 있다. 이러한 장점은 원칙대로 구현한 web app에서도 마찬가지이다.
- ROCA는 JavaScript를 제한적으로 사용한다. 따라서 앞서 이야기한 장점들을 취할 수 있다. SPA는 지도나 게임같은 복잡한 UI가 필요하기 때문에 화면에서 많은 JavaScript를 사용한다.
- ROCA는 모든 로직을 server에서 구현하도록 권고하지만, SPA는 화면이 복잡하고, 기능이 많기 때문에 시스템의 응답성을 향상시키는 것이 중요하다. 따라서 개발자가 client에서 더 많은 로직을 구현하도록 권고한다.
- ROCA는 REST 원칙 기반으로 구성되지만, SPA는 로직이 client에 있음으로 REST를 통해 다른 client들이 REST를 사용하도록 구현하기 어렵다.
3.4 ROCA 통합 옵션
- ROCA는 일반적으로 좋은 UI 레이어 디자인에 적용된다. 모놀리틱/모듈화 상관없이 web app을 구현하기 위한 규칙으로 적합하다
- ROCA는 단순화된 모듈들을 통합하는데 용이하다. HTML 기반으로 frontend가 구성되고 JavaScript는 보조적인 역할만 하기 때문에, HTML 페이지에 다른 microservice에서 비롯될 수 있는 다른 HTML 페이지에 대한 링크를 제공해 모듈화 할 수 있다.
- HTML의 각 구성 요소는 다른 microservice에서 가져올 수 있기 때문에 ROCA UI를 쉽게 모듈화할 수 있다.
- ROCA는 frontend 통합에 필요한 모든 옵션을 지원하기 때문에, ROCA는 microservice와 frontend 통합에 좋다.