상태 코드

: 클라이언트가 보낸 request의 처리 상태를 response에서 알려주는 것. 100번대 코드부터 500번대 코드까지 종류는 다양하며 각 번호대별로 다음과 같은 의미를 지닌다.

 

  • 1XX (Informational) : 요청이 수신되어 처리중
  • 2XX (Successful) : 요청이 정상적으로 처리됨
  • 3XX (Redirection) : 요청을 완료하려면 추가적인 행동이 필요함
  • 4XX (Client Error) : 클라이언트 측의 문제로 서버가 요청을 수행할 수 없음
  • 5XX (Server Error) : 서버 측 문제로 요청을 정상적으로 처리할 수 없음

 

만약, 클라이언트가 인식할 수 없는 상태 코드 즉 잘 모르는 상태 코드를 서버가 반환한다면, 클라이언트는 그걸 상위 상태코드로 해석해서 처리한다. 예를 들어 299번같은 상태코드는 "아 그냥 2XX : Successful로 뭉퉁쳐서 처리해야지~"하는 거다.


2XX - Successful

: 클라이언트의 request를 성공적으로 처리함을 알리는 상태코드.

 

  • 200 OK : 요청 성공을 의미
  • 201 Created : 요청을 성공해서 새로운 리소스가 생성됨을 의미. response message의 Location field에 새로 만들어진 리소스의 경로가 적힘
  • 202 Accepted : 요청이 접수됐으나 처리가 완료되지 않음을 의미. 예를 들면 요청 접수 후 1시간 뒤에 배치 프로세스가 요청을 처리하는 경우 등..
  • 204 No content : 서버가 request를 성공적으로 처리했으나 response message의 body에 넣어보낼 데이터가 없을 때. 예를 들어 save버튼을 눌러도 그 결과로 아무 내용이 없어도 괜찮을 때 등등..이 땐 결과 내용이 없어도 204 메시지만으로 성공여부를 식별 가능

 

3XX - Redirection

: 요청을 완료하기 위해 client의 추가적인 조치가 필요할 때

 

※ Redirection?

웹 브라우저는 3XX 응답의 결과에 Location 헤더가 있으면 그 위치로 자동적으로 이동되는데 이를 Redirect라고 한다. 예를 들어 client가 /event를 요청했지만 서버 입장에선 /event를 더 이상 안 쓰고 /new_event를 쓴다고 할 때, 서버는 3XX 응답과 함께 클라이언트를 /new_event로 redirect시킬 수 있다. 클라이언트 입장에선 브라우저가 지가 알아서 URL을 입력하고 엔터를 누른 느낌과 비슷하다. Redirection의 종류는

 

1. 영구 리다이렉션 : 특정 리소스의 URI가 영구적으로 이동. 예를 들면 /members가 아니라 /users를 쓰기로 한 경우, /members로 들어오면 /users로 리다이렉트시킨다.

  • 301 Moved Permanently : 리다이렉트 시 요청 메소드가 GET으로 변함. 따라서 본문이 제거될 수 있음(앵간하면 제거됨)
  • 308 Permanent Redirect : 301과 기능은 같으나 리다이렉트 시 기존의 요청 메소드와 본문을 유지함(처음에 POST로 보냈었으면 리다이렉트도 POST로)

2. 일시 리다이렉션 : 일시적인 변경 즉 잠깐 이동시키는 리다이렉션. 예를 들면 주문 완료 후 주문 내역 화면으로 이동하는 리다이렉션 등이 있다. 

  • 302 Fount : 리다이렉트 시 요청 메소드가 GET으로 변하고 본문이 제거될 수 있음
  • 307 Temporary Redirect : 302와 기능은 같으나 리다이렉트 시 요청 메소드와 본문 유지
  • 303 See Other : 302와 기능은 같으나 리다이렉트 시 요청 메소드가 GET으로 변하는걸 확실하게 보장

3. 특수 리다이렉션

  • 304 Not modified : 캐시를 목적으로 사용. 클라이언트가 요청한 리소스가 수정되지 않았음을 알려주는 기능. 따라서 클라이언트는 로컬PC에 저장된 캐시를 재사용할 수 있음.

참고로 영구 리다이렉션과 일시 리다이렉션은 육안으로 보기엔 비슷함. 그러나 브라우저 입장에서는 이 차이가 뚜렷하다. /members리소스가 /users로 영구적으로 바뀌었다고 하면 브라우저는 그 변화를 반영한다. 즉 영구 리다이렉션은 브라우저가 그 변화를 반영함그러나 일시 리다이렉션의 경우는 일시적으로 리소스 위치가 바뀐 거니까 브라우저가 그 변화를 반영하지 않는다. 즉 클라이언트 입장에선 일시 리다이렉션의 경우 향후 보내는 요청도 바뀐 URI가 아니라 기존 URI로 보내야 한다. 영구 리다이렉트를 서버가 하는 리다이렉트, 일시 리다이렉트를 클라이언트가 하는 리다이렉트라고도 부른다.

 

4XX - Client Error

: 클라이언트 측의 request에 잘못된 문법 등으로 서버가 요청을 수행할 수 없는 것. 오류의 원인이 클라이언트 쪽에 있음을 의미한다. 

  • 400 Bad Request : 요청 구문, 메시지 등등 오류. 요청 파라미터가 잘못 되거나 API 스펙이 맞지 않는 상황 등..클라이언트는 요청 내용을 다시 검토하고 보내야 한다.
  • 401 Unauthorized : 클라이언트가 해당 리소스에 대한 인증이 필요함을 의미. 인증(Authentication)되지 않음을 의미. 따라서 원래 이름은 Unauthentiaction이 맞는 듯..ㅠ
  • 403 Forbidden : 서버가 요청을 이해했지만 승인을 거부. 주로 인증은 됐는데 권한이 없는 상황일 때 이런 응답 코드를 받음
  • 404 Not Found : 요청 리소스를 찾을 수 없을 때. 요청 리소스가 서버에 없을 때 등등

 

5XX - Server Error

: 서버 문제로 오류가 발생한 것

  • 500 Internal Server Error : 서버 내부 문제로 오류가 발생함을 의미. 애매하면 걍 다 500 오류임
  • 503 Service Unavailable : 서버가 일시적 과부하 또는 예정된 작업으로 잠시 요청을 처리할 수 없을 때

 

4XX 에러는 클라이언트 쪽 문제니까 다시 시도해도 똑같이 안 되지만, 5XX에러는 서버 측 문제라 다시 하면 될 수도 있다는 차이점이 있다.

 

 

 

1. 클라이언트 - 서버 구조

: HTTP는 클라이언트가 request를 보내면 서버가 response를 보내는 구조이다. 즉 클라이언트와 서버가 개념적으로 분리된 형태이며, 클라이언트로부터 request가 안오면 서버는 자신의 힘으로 클라이언트 측으로 HTTP메시지를 보낼 수 없다는 얘기다.(HTTP는 서버가 클라이언트에게 먼저 메시지를 보낼 수 없고 클라이언트의 요청메시지에 대한 응답만 할 수 있다는 이야기임)

 

2. 무상태 프로토콜(stateless)이다

: HTTP는 서버가 클라이언트의 상태를 보존하지 않는 stateless한 프로토콜이다.

 

stateful, 즉 상태를 유지한다고 하면 서버는 클라이언트의 이전 상태를 기억한다. 쉽게 말해 내가 친구랑 맥북에 대해 대화하다가 "그거 살까?"라고 했다면 친구는 '그거'가 맥북을 지칭한다는 것을 알고 있다.stateless, 상태를 유지하지 않는다면 서버는 클라이언트의 이전 상태를 기억 못 한다. 내가 친구랑 맥북에 대해 대화하다가도 "그거 살까?"라고 했을 때 친구는 '그거'가 맥북을 말하는 건지 아이폰을 말하는건지 아이패드를 말하는 건지 모른다는 뜻이다. 따라서 이 상태라면 친구에게 "그거 살까?"가 아니라 "맥북 살까?"라는 식으로 대화해야 한다.

 

즉, stateless는 서버가 이전 상태를 기억하지 못 하기 때문에 매 요청 시마다 필요한 데이터를 몽땅 다 넘겨야 한다! 때문에 얼핏 보면 stateless방식은 전송하는 데이터 양이 더 많으니까 안 좋은 거 아닌가?할 수 있지만 이 방식은 서버 확장성이 높다는 엄청난 장점을 가진다. 생각해보면, stateful방식은 내가 재준이한테 맥북 얘기하다가 다훈이한테 가서 "그거 살까?"라고 하면 다훈이는 그게 뭔데 임마라고 하겠지만, stateless방식은 재준이한테 맥북 얘기하다가 다훈이한테 가서 "맥북 살까?"라고 얘기해도 괜찮다. 즉 stateless방식은 응답 서버를 쉽게 바꿀 수 있는 것이다. 때문에 클라이언트 요청이 폭증해도 서버를 대거 투입할 수 있으며 이론상 무한한 서버 증설이 가능하다. stateful방식은 클라이언트가 서버 A와 통신하기 시작했다면 계속 그 놈과 통신해야 하지만 stateless방식은 아무 서버나 입맛대로 호출해도 된다는 것.

 

3. 비연결성

: 연결을 유지한다는 것은 이는 클라이언트-서버 간에 딱히 주고받을 것이 없는 순간에도 계속해서 TCP/IP연결을 맺고 있는 걸 말하고 이는 서버의 자원을 소모하는 것을 의미한다. HTTP는 기본적으로 연결을 유지하지 않는다 즉 볼일이 끝나면 TCP/IP연결을 종료한다. 이로 인해 최소한의 서버 자원을 유지할 수 있음이 보장된다. 같은 시간동안 수천 수만 명이 서비스를 사용하다 특정 시간대에 서버에서 처리되고 있는 요청은 매우 적을 것이다(검색 기능이 있다고 할 때 동시에 검색 기능을 누르는 일은 많지 않은 것처럼). 따라서 이 비연결성 특성을 통해 서버 자원을 매우 효율적으로 이용할 수 있게 된다.

 

 그러나 이런 비연결성의 단점은 자원 요청 시마다 매번 TCP/IP 연결을 맺어야 하는데 이 작업은 3 way handshake가 수반되므로 overhead가 누적될 수밖에 없다는 것. 이 문제점은 HTTP 지속 연결(Persistent Connections)로 해결됐다.

 

4. 단순하고, 확장 가능하다

 

  일반적으로 서비스를 요청하는 측을 클라이언트, 제공하는 측을 서버라고 한다. 웹 브라우저, 메일 프로그램 등은 사용지 측에서 사용하는 클라이언트 애플리케이션이고, 웹 서버 프로그램이나 메일 서버 프로그램 등은 서버 측에서 쓰는 서버 애플리케이션이라 볼 수 있다. 이러한 애플리케이션은 모두 응용 계층(application layer)에서 동작한다.

 

  물리 계층, 데이터링크 계층, 네트워크 계층, 전송 계층을 통해 상대방에게 데이터를 정확하게 전달할 수 있다는 것을 알게 됐다. 응용 계층은 애플리케이션과 데이터를 주고받기 위해 필요한 부분으로, 클라이언트의 요청(request)를 전달하기 위해 통신 대상(서버 등)이 이해할 수 있는 메세지(데이터)로 변환하고 이를 전송 계층으로 전달하는 역할을 한다. 웹 브라우저, 메일 프로그램 등과 같은 클라이언트 측 애플리케이션이 서버 측 애플리케이션과 통신하려면 응용 계층의 프로토콜을 사용해야 한다. 웹 사이트를 볼 땐 HTTP, 파일을 전송할 땐 FTP, 메일을 보낼 땐 SMTP, 메일을 받을 때는 POP3라는 프로토콜을 사용한다. 암튼 결국, 응용 계층은 각각의 애플리케이션에 대응되는 데이터를 전송 계층으로 전달하는 역할을 한다. 

 

HTTP란?

  클라이언트(웹 브라우저)는 웹 사이트를 보기 위해 서버(웹 서버 프로그램)의 80번 포트를 사용해 HTTP통신을 한다. 클라이언트 측에서 HTTP request를 보내고, 서버 측에서 HTTP response를 반환하는 식이다. 지금은 HTTP/2나 HTTP/1.1버전을 사용하지만 옛날에 쓰던 HTTP/1.0버전에서는 요청을 보낼 때마다 연결했다가 응답이 오면 연결을 끊고, 요청을 또 보내게 되면 새롭게 연결하는 방식을 사용했으나 HTTP/1.1버전부터는 keepalive라는 기능이 추가되면서 연결이 한 번 되면 데이터 교환을 마칠 때까지 연결을 유지하는 방식이 가능하게 됐다. HTTP/1.1버전은 요청을 보낸 순서대로 응답을 반환한다는 특징이 있어서 이전 요청을 처리하는 시간이 길어지면 다음 요청이 밀리는 단점이 있었는데. 2.0버전부터는 순서대로 응답을 반환할 필요가 없어져서 콘텐츠를 더욱 빠르게 표시할 수 있게 됐다.

 

DNS?

  특정 사이트를 보고싶으면 특정 IP주소를 통해 웹 서버에 접속해 웹 사이트를 보는게 맞다. 네이버에 가고 싶으면 주소창에 www.naver.com을 쳐서 웹사이트를 본다. ..? 뭔가 이상하지 않은가? 네이버의 IP주소가 아니라 다른 걸 입력했는데 네이버의 웹사이트를 보고 있는 셈이니 말이다. 이것이 DNS덕분이다. 간단히 말해 DNS는 URL을 IP주소로 변환하는 시스템이다. www로 시작하는 저 url대신에 실제 네이버의 IP주소를 통해서도 물론 웹 서버에 요청을 보낼 수 있지만 네이버, 다음, 구글 등의 IP주소를 하나하나 기억하는 것은 쉬운 것이 아니다. 예를 들어 뭐..친구들 전화번호 다 외우고 있는 사람 없을 것이다. 다 전화번호부에 이름으로 저장해서 그 이름에 전화걸지..일일이 전화번호 외워서 전화거는 사람은 별로 없을 거란 얘기. DNS는 즉 일종의 전화번호부라고 생각할 수도 있겠다. 아무튼 특정 url을 사용해 웹 서버에 접속하도록 돕는 것을 DNS의 이름 해석이라고 말하며, 이는 내가 원하는 url의 IP주소를 알려주는 것을 의미한다. url을 입력하면 컴퓨터가 먼저 DNS서버에게 이 url의 IP주소를 알려달라고 요청하고, DNS서버는 컴퓨터에게 그 url의 IP주소를 반환한다. 이를 이용해 그 IP주소로 접속할 수 있는 것.

 

메일 서버의 구조

  메일을 송수신하기 위해서는 클라이언트 측의 메일 프로그램과 서버 측의 메일 서버 프로그램 간에 통신을 해야 한다. 이 때 사용되는 프로토콜의 종류에는 두 가지가 있는데 첫째는 메일을 보내는데 사용되는 SMTP고 둘째는 메일을 받는데 사용되는 POP3다. SMTP는 포트번호로 25번을, POP3는 포트 번호로 110번을 사용한다. 좀 더 정확히 설명하자면 컴퓨터 A, B와 메일 서버1, 메일 서버 2가 있을 때 SMTP를 이용해 A에서 메일서버1로 메일을 보내고, 마찬가지로 SMTP를 이용해 메일서버1에서 메일서버2로 메일을 보낸다음 POP3를 이용해 메일서버2에서 B로 메일을 보낸다. 

 

SMTP에 의한 메일 송신

  다음과 같은 순서로 진행된다

 

1) 세션 시작 통지

2) 송신자의 메일 주소 통지

3) 목적지 메일 주소 통지

4) 메일 본문 전송 통지

5) 메일 본문 송신

6) 세션 종료 통지

 

각 과정마다 응답을 받은 후 다음 과정이 진행되는 식. 방금 살펴본 것이 컴퓨터 A에서 메일서버1로 보내는 과정이었고, 메일서버1에서도 SMTP를 이용해 메일 서버2로 메일을 보낸다.

 

POP3에 의한 메일 수신

  메일 서버에는 메일 박스라고 불리는 메일을 보관해 주는 기능이 있다. 메일 서버2는 POP3를 사용해 메일 서버2의 메일박스에서 메일을 가져와 컴퓨터 B로 전송한다. B입장에서 메일 서버2로부터 메일을 수신할 때는 사용자 이름과 비밀번호를 이용한 사용자 인증이 필요하다. POP3 프로토콜로 110번 포트를 사용한다. POP3는 다음과 같은 순서로 진행된다. B가 메일서버2에게

 

1) 세션 시작 통지 -> 메일서버2가 확인응답 보냄

2) 수신자의 사용자이름 통지 -> 메일서버2가 확인응답 보냄

3) 수신자의 비밀번호 통지  -> 메일서버2가 확인응답 보냄

4) 메일을 확인  -> 메일서버2가 "있음"이라는 확인응답 보냄

5) 메일의 전송 요청 -> 메일서버2가 메일내용 전송

6) 세션 종료 요청

+ Recent posts