RESTful 하다는 것은 무엇일까?

Gn0lee·2024년 12월 5일
0

Tech 이모저모

목록 보기
20/21

실무를 진행하다보면 자연스럽게 API에 관한 이야기를 많이 하게 됩니다. 'PUT이 아니라 DELETE를 사용해야 할 것 같은데..', '이 경로가 맞나..?' 등 무언가 어색한 지점이 있기 마련입니다. 이런 표현은 대부분 RESTful 하지 않다로 함축할 수 있는 경우가 많습니다. 하지만 저는 REST에 대해 정확히 모르고 있기 때문에 항상 길게 풀어서 설명하곤 했습니다. 이번 기회에 REST에 대해 알아보고 어떤 경우에 RESTful 하지 못하다 할 수 있는지 정리해 보려 합니다.

REST의 정의

REST는 Roy Fielding이 2000년에 제안한 개념입니다. 이 개념은 현대 웹 서비스 설계의 기본이 되었습니다. 우선 REST는 Representational State Transfer 의 약자로 직역하면 표현적 상태 전달입니다. 이렇게만 보면 무슨 말인지 잘 모르겠으니 REST의 내용을 살펴보며 왜 해당 약자를 사용했는지 살펴보겠습니다.

리소스와 표현

우리가 서비스를 구축할 때 리소스가 필요합니다. 예를 들어 서비스에 가입한 유저의 정보를 조회할 때 서버는 DB 내용을 그대로 전달하지 않습니다. 대신 JSON, XML, HTML등으로 변환하여 전달합니다. 그래서 HTTP 헤더의 Accept 필드를 통해 어떤 표현 방식으로 응답을 받을 것인지 지정해 줍니다. 예를 들면 아래와 같은 방식으로 전달합니다.

{
    "id": 123,
    "name": "Lee Jinho",
    "email": "jinho@example.com"
}
<user>
    <id>123</id>
    <name>Lee Jinho</name>
    <email>jinho@example.com</email>
</user>

상태

REST에서 상태는 클라이언트와 서버 간의 상호작용에서 애플리케이션, 리소스의 상태를 의미합니다. 우선 애플리케이션 상태는 클라이언트가 현재 어떤 작업을 수행하고 있는지에 대한 정보입니다. 상태는 클라이언트 측에 존재하며, 클라이언트는 서버에서 받은 리소스 표현을 바탕으로 애플리케이션 상태를 관리합니다. 예를 들어 사용자가 특정 상품 페이지를 보고 있다면, 그 상품과 관련된 정보가 클라이언트 상태에 해당합니다. 리소스의 상태는 서버에 저장된 리소스의 현재 값이나 속성을 뜻합니다. 클라이언트는 API를 통해 이 상태를 조회, 변경,삭제할 수 있습니다.

아래는 REST를 바탕으로 상태를 변화하는 과정입니다.

  1. 사용자가 REST API를 통해 특정 리소스를 요청
    GET /users/123
  2. 사용자가 이메일을 변경
    PUT /users/123 요청으로 새로운 이메일 전송
  3. 클라이언트가 새로운 상태를 요청
    GET /users/123 를 통해 서버가 최신 정보를 반환

Stateless

REST에서는 이러한 상태를 Stateless하게 관리합니다. 우선 Stateless란 클라이언트와 서버의 요청-응답 관계에서 서버가 클라이언트의 상태를 유지하지 않는 것을 의미합니다. 즉 각 요청은 완전히 독립적이며, 필요한 모든 정보를 포함해야 서버가 요청을 처리할 수 있습니다. 그렇다면 REST에서는 왜 Stateless 하게 상태를 관리하는지 알아보았습니다.

  1. 확장성 (Scalability)
    서버가 클라이언트의 상태를 유지하지 않기 때문에, 요청이 늘어나더라도 서버 간 부하 분산이 쉽습니다.
    클라이언트 요청은 어떤 서버로든 분배할 수 있습니다. 즉, 특정 서버에 의존하지 않으므로 로드 밸런싱이 원활합니다.
    예: 클라이언트 A의 첫 요청은 서버 X, 두 번째 요청은 서버 Y가 처리해도 문제가 없음.
  2. 단순성 (Simplicity)
    서버는 클라이언트 상태를 관리하지 않으므로 더 간단한 설계와 구현이 가능합니다.
    서버는 들어온 요청만 처리하면 되며, 이전 요청이나 세션 데이터를 참조할 필요가 없습니다.
    예:GET /users/123 요청만으로 충분한 정보를 전달받아 응답 생성.
  3. 안정성 및 신뢰성 (Reliability)
    서버가 상태를 관리하지 않으므로, 서버 간 동기화 문제가 발생하지 않습니다.
    한 서버가 다운되더라도 클라이언트는 다른 서버로 요청을 보내 계속 작업을 이어갈 수 있습니다.
    세션 유지가 필요 없는 구조는 장애 복구를 더 쉽게 만듭니다.

더 많은 이유가 있지만 가장 큰 이유가 위 3가지 이유라 생각합니다. 하지만 Stateless하게 상태를 관리하면 각 요청마다 서버에서 상태를 알기 위한 데이터를 모두 포함해야하기 때문에 요청크기가 커지게 됩니다. 또한 서버는 단순해지지만 클라이언트는 상태를 유지하기 위해 더 복잡해 집니다. 이러한 단점을 보완하기 위해 토큰, 클라이언트의 저장공간(로컬스토리지 등), 프록시 서버등을 이용합니다.

REST의 정의

따라서 REST는 아래와 같이 정리할 수 있습니다.

리소스의 표현(Representational)을 통해 애플리케이션 상태(State)전달(Transfer)한다

RESTful 하다는 것은 무엇일까?

그렇다면 API가 어떤 경우에 RESTful하지 않다고 하는지 간단한 예시와 함께 정리해보았습니다.

  1. URI에 동작이 포함되는 경우
  • 잘못된 예: GET /getUserDetails
  • 올바른 예: GET /users/123
  1. 일관성 없는 HTTP 메서드 사용
  • 잘못된 예: POST /users/123 → 리소스 삭제
  • 올바른 예: DELETE /users/123
  1. 계층 구조를 따르지 않는 경우
  • 잘못된 예: GET /users/123/getOrders → 동작이 포함되며 계층적 관계를 포함하지 못함
  • 올바른 예: GET /users/123/orders
  1. 상태를 URI에 포함하는 경우
  • 잘못된 예: GET /users/123?sessionId=abc123
  • 올바른 예: GET /users/123 → 헤더나 쿠키 사용
  1. 모든 작업에 POST만 사용하는 API

  2. 에러 응답 코드 오용

  • 잘못된 예: 에러 상태를 200으로 반환
  • 올바른 예: 에러 종류에 맞는 상태 코드를 사용

REST 구조는 더 복잡하지만 이러한 경우들에 RESTful 하지 못하다고 할 수 있을 것 같습니다.

profile
정보보다는 경험을 공유하는 테크 블로그입니다.

0개의 댓글