마이크로서비스 모델링 ⑥ : BackEnd 설계 -API설계

Updated:

마이크로서비스 모델링 ⑥ : 백엔드 모델링

벡엔드 마이크로서비스를 위한 설계는 헥사고널 아키텍처를 적용해서 외부 영역과 내부 영역으로 구분되어 진행된다. 이전 포스트에서 설명했던 이벤트 스토밍 결과를 반영하여 다음과 같이 백엔드 마이크로서비스의 내부를 헥사고널 구조를 정의하고 매핑시 킬수 있으며 이를 기반으로 발전시켜 나갈 수 있다.

아래 그림과 같이 이벤트 스토밍의 ‘커맨드’는 헥사고널의 인바운드 어답터의 하나인 REST API가 되며 ‘어그리게잇’은 헥사고널의 내부영역인 도메인 모델이 되며 ‘도메인이벤트’는 헥사고널 외부 영역의 아웃바운드 메시지 처리 어답터의 처리 대상이 되고 ‘외부 시스템’은 마찬가지로 아웃바운드 어답터가 호출해야 할 외부 연계 시스템으로 매핑 된다.

이벤트 스토밍 결과와 헥사고널 아키텍처 구성요소 매핑

그렇지만 이러한 요소는 백엔드 모델링의 시발점이 될 분이며 구현을 위해서는 좀 더 구체적인 설계가 필요하다. 따라서 외부영역설계는 프론트엔드와 연계되는 ‘API설계’ 로, 내부 영역은 비지니스 로직을 구현하는 ‘도메인모델링’, ‘데이터모델링’ 으로 구체화되어 진행된다. API설계부터 살펴본다.

API 설계

마이크로서비스팀은 서비스가 제공하는 기능에 대한 프론트와 백엔드의 구현을 모두 책임지며, 프론트 /백엔드 엔지니어가 하나의 팀에서 긴밀하게 협업해야 한다.
이러한 협력을 위해서 프론트와 백엔드의 연계를 위한 계약이 필요한데 이것이 API설계이다. API는 백엔드 서비스에 존재하지만 프론트의 요구사항을 충족하도록 정의되어야 한다.

API영역은 앞서 언급한 바와 같이 헥사고널의 외부 영역이며 인바운드 아답터로써 어떠한 호출 방식도 허용되는 유연한 공간이다. 그렇지만 최근의 추세는 http프로토콜과 JOSN포맷을 사용하는 REST API가 표준처럼 많이 사용되고 있다. 이는 REST API방식이 대중적인 http프로토콜 그리고 취급하기 쉬운 JOSN포맷 그리고 HTTP 간단한 메소드 형식등을 가지고 있어 쉽고 명괘하여 누구나 이해 가능한 기준을 제공하기 때문이라고 본다. 그럼 이러한 REST API 방식에 대해 살펴보자.

REST API개념

REST(Representational State Transfer) API는 Http프로토콜을 사용하는 대중적으로 광범위한 지지를 얻은 네트워크 기반 아키텍처 스타일이다. 아키텍처를 표현하는 구성요소로 자원(Resource)과 행위(Verb) , 표현(Representations)으로 이루어 진다. 예를 들어 설명하면 홍길동이라는 사용자를 생성한다.라는 API가 필요하다면 자원은 ‘사용자’이고 행위는 ‘생성한다’ 이고 표현은 ‘홍길동’이 된다. 이를 REST API로 표현하면 다음과 같다.

HTTP POST , http://xxx.com/users/
{
“users”:{
	        “name”:”홍길동”
}
}

즉 자원은 http://xxx.com/users/라는 URI로 표현되고 생성을 위한 http 메소드인 POST를 사용하였고, JOSN문서형태로 구체적인 사용자로 표시(전달) 된 것이다.

이렇게 REST API는 직접적인 사용의 주체가 되는 요소를 자원이라 하며 URI 포맷으로 표현한다. 자원은 명사를 사용하며 세부항목을 표시할 때는 뒤에 ID를 붙여 정의한다. 즉 사용자의 리소스 형태가 /users/이고 홍길동의 식별자가 ‘01’이라면 홍길동은 /users/01 로 표현된다.

또한 이러한 API를 사용하기 위한 입출력 데이터로 JOSN포맷을 활용한다. 그리고 행위를 표현하기 위해 http 메소드를 활용한다. 예를 들면 아래와 같이 REST API의 구성요소인 자원, 메소드, 표현방식을 정리할 수 있다.

GET 리소스 전체 조회 HTTP GET http://xxx.com/users/

{
  “users”: [
        {
           “id”: 01,
	        “name”: “홍길동”
        },
        {
           “id”: 02,
	        “name”: “장백산”
        }
          ]
}

GET 개별 항목 조회 HTTP GET http://xxx.com/users/01

{
  “users”: [
          {
           “id”: 01,
	        “name”: “홍길동”
          }
           ]
}

POST 추가 HTTP POST http://xxx.com/users/

요청
{
“users”:{
	        “name”:”김유신”
        }
}    

결과
{
“users”: [
        {
           “id”: 03,
	        “name”: “김유시”
        }
        ]
}

PUT 수정 HTTP PUT http://xxx.com/users/01

요청
{
“users”:{
	        “name”:”임꺽정”
        }
}

결과
{
“users”: [
        {
           “id”: 01,
	        “name”: “임꺽정”
        }
        ]
}

DELETE 삭제 HTTP DELETE http://xxx.com/users/01 삭제됨

이와 같이 REST API의 구성요소만 보고 API의 내용을 직관적으로 이해 할 수 있기 때문에 최소한의 문서로써 설명할 수 있으며 매우 쉽게 사용할 수 있다.

REST API 성숙도


마틴 파울러가 이러한 REST API를 설명하기 위해 리처드슨 REST API성숙도 모델을 인용했는데 다음과 같다.

  • 레벨0 는 REST API의 매커니즘을 전혀 사용하지 않고 전통적인 원격 프로시저 호출(Remote Procedure Call)방식으로 HTTP프로토콜만을 사용한 것이다. 상품서비스를 예로 들자면 예전에 많이 사용했던 방식인데 /ProductService?Flag=create 처럼 하나의 URI주소 에 GET방식으로 URI매개변수로 Flag로 두어 입력,수정,삭제를 처리했던 방식이다. 개발자가 백엔드 내부에서 비지니스 로직을 통해 어떠한 결정을 하는지 사용자는 API를 보고는 알 수 없기 때문에 API 사용을 위한 명세가 필요하다.
  • 레벨1 은 URI에 개별적인 자원을 표현하는 것이다. 여러 기능 사용을 위해 하나의 URI에 요청하지 않고 요청이 필요한 대상을 특정한다. 상품 중 사과정보를 제공하는 URI는 다음과 같다. /Products/apple 이로써 사용자는 이렇게 특정 리소스가 어떠한 정보를 제공하는 지 인지할 수 있다.
  • 레벨2 는 서비스의 기능 처리를 위해 약속된 HTTP 메소드들을 사용 하는 것이다. 물론 레벨0,1도 HTTP 메소드를 사용했지만 GET,POST로 모든 것을 처리하던지 어떤 방식을 사용하는지는 개발자에 따라 달랐다. 레벨2에서는 약속된HTTP사용법 에 가능한 가깝게 사용한다. 위에 언급한 예시처럼 조회,추가,수정,삭제 기능을 HTTP 메소드 인 GET,POST,PUT,DELETE로 처리한다. API사용자는 리소스에 어떠한 메소드를 던지면 어떠한 행위가 발생되는지 인지할 수 있다.
  • 레벨3 는 HATEOAS(Hypertext As The Engine Of Application State)라는 어려워 보이는 약자로 정의되는데 이 방식은 특정 요청을 하게 되면 반환값에 기대했던 결과에 덧붙여추가로 사용자가 그 다음에 무엇을 할 수 있는 지와 그것을 하기위해 다룰 수 있는 URI값을 보내준다. 즉 사용자에게 좀더 리소스를 탐색하여 활용할 수 있는 가능성을 제공한다.
  • 아래와 같이 그림으로 리처드슨 REST API 성숙도를 표현할 수 있다.

리처드슨 REST API 성숙도

API문서화


애자일 모델링 방식의 추구로 가급적이면 불필요한 설계물을 남기는 것은 바람직하지 하지 않다. 산출물의 필요성은 항상 공유와 협업 측면에서 고려하자. 그렇다면API설계는 프론트 엔드 엔지니어와 백엔드 엔지니어의 협업 차원에서 중요하다. 또한 API설계는 다른 프론트/백엔드 단의 상세 설계에 앞서서 진행될 필요도 있다. 따라서 다른 설계 요소에 비해 공유가 중요하다. 협업 시스템이 존재한다면 간단히 위키(wiki) 형태의 문서로 작성할 수도 있다. 공식적인 문서 형식이 필요하다면 아래와 같이 엑셀 형태가 편리하다. 어떠한 형태를 사용하던지 최소 다음 항목들은 포함하도록 하자

  • 서비스 명, API명, 리소스(URI)
  • Request, Response 매개변수
  • Request, Response 샘플

API설계서 양식