티스토리 뷰

책/misc

3장. HTTP 메시지

kingsubin 2022. 5. 2. 22:56

3장. HTTP 메시지

3.1 메시지의 흐름

  • HTTP 메시지는 HTTP 애플리케이션 간에 주고받은 데이터들의 블록들이다.
  • 요청, 응답 관계없이 모든 메시지는 다운스트림으로 흐른다.
  • 발송자는 수신자의 업스트림이다.

3.2 메시지의 각 부분

  • 메시지는 시작줄, 헤더 블록, 본문 세 부분으로 이루어진다.
  • 시작줄, 헤더는 줄 단위로 분리된 아스키 문자열이다.
  • 줄바꿈 문자열은 ‘CRLF’라고 쓴다.
  • 본문은 선택적인 데이터 덩어리이다.
  • 시작줄이나 헤더와 달리 본문은 텍스트나 이진 데이터를 포함할 수도 있고 비어있을 수도 있다.

메시지 문법

// 요청 메시지 형식
<메서드> <요청URL> <버전>
<헤더>

<본문>
// 응답 메시지 본문
<버전> <상태코드> <사유구절>
<헤더>

<본문>
  • 헤더나 본문이 없더라도 HTTP 헤더의 집합은 항상 CRLF 로 끝나야 함을 주의하라.
  • 규칙을 잘 지키지 않는 구현체와의 호환을 위해 CRLF 없이 끝나는 메시지도 받을 수 있게 해야한다.

시작줄

  • HTTP는 쉽게 확장할 수 있도록 설계되었기에 서버는 그들만의 메서드를 추가 구현할 수 있다. 이러한 추가 메서드는 HTTP 명세를 확장하는 것이기에 확장 메서드라고 한다.
  • 사유 구절에는 어떤 엄격한 규칙도 제공하지 않는다.

전체 범위 정의된 범위 분류

100-199 100-101 정보
200-299 200-206 성공
300-399 300-305 리다이렉션
400-499 400-415 클라이언트 에러
500-599 500-505 서버 에러

헤더

  • <K, V>의 목록이다.

본문

  • HTTP 메시지의 화물

3.3 메서드

  • 모든 서버가 모든 메서드를 구현하지는 않는다.

안전한 메서드

  • GET, HEAD 메서드를 사용하는 요청은 서버에 어떤 작용도 없다. (사실 웹 개발자에 달렸음.)
  • 이러한 메서드들을 안전한 메서드라 불리는 메서드 집합이라 한다.
  • 안전한 메서드의 목적은, 서버에 어떤 영향을 줄 수 있는 안전하지 않은 메서드가 사용될 때 사용자들에게 그 사실을 알려주는 애플리케이션을 만들 수 있도록 하는 것에 있다.

GET

  • 서버에게 리소스를 달라고 요청하기 위해 쓰인다.
  • HTTP/1.1 은 이 메서드를 구현할 것을 요구한다.

HEAD

  • GET 처럼 행동하지만, 서버는 응답으로 헤더만을 돌려준다.
  • 서버 개발자는 반환하는 헤더가 GET 요청과 정확히 일치함을 보장해야 한다.
  • HTTP/1.1 준수를 위해서 반드시 구현되어 있어야 한다.

PUT

  • 메서드의 의미는 서버가 요청의 본문을 가지고 새 문서를 만들거나, 이미 존재한다면 교체하는 것이다.

POST

  • 서버에 입력 데이터를 전송하기 위해 설계되었다.

TRACE

  • 클라이언트가 요청을 할 때, 그 요청은 방화벽, 프록시, 게이트웨이 등의 애플리케이션을 통과할 수 있다. 이 들에게는 요청을 수정할 기회가 있다. TRACE 메서드는 클라이언트에게 자신의 요청이 서버에 도달했을 때 어떻게 보이게 되는지 알려준다.
  • TRACE 요청은 목적지 서버에 ‘루프백(loopback)’ 진단을 시작한다. 요청의 마지막 단계에 있는 서버는 자신이 받은 요청 메시지를 본문에 넣어 TRACE 응답을 되돌려준다. 클라이언트는 자신과 서버 사이에 있는 모든 HTTP 요청/응답 을 추적할 수 있다.
  • 주로 진단을 위해 사용된다. 예를 들어 요청이 의도한 요청/응답 연쇄를 거쳐가는지 검사할 수 있다.
  • 진단을 위해 사용할 때는 괜찮지만, 중간 애플리케이션이 다른 종류의 메서드들을 일관되게 다룬다고 가정하는 문제가 있다.
  • TRACE는 메서드를 구별하는 메커니즘을 제공하지 않는다.
  • 본문을 보낼 수 없다.

OPTIONS

  • 이 메서드는 웹 서버에게 여러 가지 종류의 지원 범위에 대해 물어본다.
  • 서버에게 특정 리소스에 대해 어떤 메서드가 지원되는지 물어볼 수 있다.
// request
OPTIONS * HTTP/1.1
Host: www.joes-hardware.com
Accept: *

// response
HTTP/1.1 200 OK
Allow: GET, POST, PUT, OPTIONS
Context-length: 0

DELETE

  • 요청 URL로 지정한 리소스 삭제를 요청한다.
  • 클라이언트는 삭제가 수행되는 것을 보장하지 못한다. 왜냐면 HTTP 명세는 서버가 클라이언트에게 알리 지 않고 요청을 무시하는 것을 허용하기 때문이다.

확장 메서드

  • HTTP 는 필요에 따라 확장해도 문제가 없도록 설계되어 있으므로, 새로 기능을 추가해도 과거에 구현된 SW의 오동작을 유발하지 않는다.
  • 대부분의 HTTP 확장을 다룰 때는 ‘엄격하게 보내고 관대하게 받아들여라' 라는 규칙을 따르는것이 가장 좋다.

3.4 상태 코드

  • 사유 구절을 정확하게 쓰는 가이드는 존재하지 않지만 여기서는 HTTP/1.1 명세에서 추천하는 사유 구절을 포함한다.

100-199: 정보성 상태 코드

  • 100: Continue
    • 요청의 시작 부분 일부가 받아들여졌으며, 클라이언트는 나머지를 계속 이어 보내야 함을 의미
  • 101: Switching Protocols
    • 클라이언트가 Upgrade 헤더에 나열한 것 중 하나로 서버가 프로토콜을 바꾸었음을 의미

클라이언트와 100 Continue

  • 클라이언트는 100-continue를 서버가 다루거나 사용할 수 없는 큰 엔티티를 서버에게 보내지 않으려는 목적으로만 사용해야 한다.
  • 클라이언트는 예상하지 못한 100-continue 응답에도 대비해야 한다. (잘못 만들어진 앱은 이 코드를 부적절하게 보냄.)

서버와 100 Continue

  • 서버가 100-continue 값이 담긴 Excpect 헤더가 포함된 요청을 받으면, 100-continue 응답 혹은 에러 코드로 답해야 한다.
  • 서버는 100-continue 응답을 받을 것을 의도하지 않은 클라이언트에게 100-continue 상태코드를 보내면 안된다.

200-299: 성공 상태 코드

  • 200: OK
    • 요청은 정상이고, 엔티티 본문은 요청된 리소스를 포함하고 있다.
  • 201: Created
    • 개체를 생성하라는 요청을 위한 것.
    • 생성된 리소스에 대한 최대한 구체적인 참조가 담긴 Location 헤더와 함께, 그 리소스를 참조할 수 있는 URL을 엔티티 본문에 포함해야 한다.
    • 서버는 상태 코드를 보내기에 앞서 반드시 객체를 생성해야 한다.
  • 202: Accepted
    • 요청이 받아들여졌다 라는 의미
    • 서버는 엔티티 본문에 요청에 대한 상태와 가급적이면 요청의 처리가 언제 완료될 것인지에 대한 추정도 포함해야 한다.
  • 203: Non-Authoritative Infromation
    • 엔티티 헤더에 들어있는 정보가 원래 서버가 아닌 리소스의 사본에서 왔다. 라는 의미
    • 필수적인 응답코드는 아님. 200 상태였을 애플리케이션을 위한 선택사항
  • 204: No Content
    • 응답 메시지는 헤더와 상태줄을 포함하지만 본문은 포함하지 않는다.
    • 주로 웹브라우저를 갱신하고자 할 때 사용한다.
  • 205: Reset Content
    • 브라우저에게 현재 페이지에 있는 HTML 폼에 채워진 모든 값을 비우라고 말한다.
  • 207: Partial Content
    • 범위 요청이 성공했음을 의미한다.
    • Content-Rage, Date 헤더를 반드시 포함해야 하며, Etag, Content-Location 중 하나의 헤더도 반드시 포함해야 한다.

300-399: 리다이렉션 상태 코드

  • 클라이언트가 관심있어 하는 리소스에 대해 다른 위치를 사용하라고 말해주거나 그 리소스 내용 대신 다른 대안 응답을 제공한다.
  • 만약 리소스가 옮겨졌다면, 어디서 찾을 수 있는지 알려주기 위해 리다이렉션 상태코드와 Location 헤더를 보낼 수 있다.
  • 유사한 상태코드가 있는데 HTTP 버전 때문에 생긴 문제이며, 서버는 적절한 리다이렉트 상태코드를 선택하기 위해서는 클라이언트의 HTTP 버전을 검사할 필요가 있다.
  • 300: Multiple Choices
    • 클라이언트가 동시에 여러 리소스를 가리키는 URL 요청시 그 리소스의 목록과 함께 반환한다.
    • ex. 어떤 서버가 하나의 HTML 문서를 영어와 프랑스어로 모두 제공하는 경우
  • 301: Moved Permanently
    • 요청 URL이 옮겨졌을 때 사용한다.
    • 응답은 Location 헤더에 현재 리소스가 존재하고 있는 URL을 포함해야 한다.
  • 302: Found
    • 301 코드와 같다. 그러나 클라이언트는 Location 헤더에 주어진 URL을 리소스를 임시로 가리키기 위한 목적으로 사용해야 한다.
  • 303: See Other
    • 클라이언트에게 리소스를 다른 URL에서 가져와야 한다고 말해주고자 할 때 쓰인다.
    • 주 목적은 POST 요청에 대한 응답으로 클라이언트에게 리소스 위치를 알려주는 것이다.
  • 304: Not Modified
    • 클라이언트가 조건부 요청을 보냈고 요청한 리소스가 최근에 수정된 일이 없다면, 이 코드는 리소스가 수정되지 않았음을 의미하게 된다.
    • 엔티티 본문을 가져서는 안된다.
  • 305: Use Proxy
    • 리소스가 반드시 프록시를 통해서 접근되어야 함을 나타내기 위해 사용한다.
  • 306
    • 사용되지 않음
  • 307: Temporary Redirect
    • 301과 비슷하다. 그러나 클라이언트는 Location 헤더에 주어진 URL을 리소스를 임시로 가리키기 위한 목적으로 사용해야 한다.

400-499: 클라이언트 에러 상태 코드

  • 400: Bad Request
    • 클라이언트가 잘못된 요청을 보냈음.
  • 401: Unauthorized
    • 클라이언트에게 스스로 인증하라고 요구하는 내용의 응답을 적절한 헤더와 함께 반환한다.
  • 402: Payment Required
    • 미래를 위해 만들어둠.
  • 403: Forbidden
    • 서버에 의해 거부되었음. 이유를 설명하는 엔티티 본문을 포함시킬 수도 있는데 보통 서버가 거절 이유를 숨기고 싶을때 사용한다.
  • 404: Not Found
    • 서버가 요청한 URL을 찾을 수 없음을 알려주기 위해 사용한다.
  • 405: Method Not Aollowed
    • 요청한 URL에 대해 지원하지 않는 메서드로 요청받았을 때 사용한다.
  • 406: Not Acceptable
    • 주어진 URL에 대한 리소스 중 클라이언트가 받아들일 수 있는 것이 없는 경우 사용한다.
  • 407: Proxy Authentication Required
    • 401과 비슷함. 리소스에 대해 인증을 요구하는 프록시 서버를 위해 사용한다.
  • 408: Request Timeout
    • 요청 완수하기에 시간이 너무 많이 걸리는 경우, 이 코드로 응답하고 연결을 끊을 수 있다.
  • 409: Conflict
    • 요청이 충돌을 일으킬 염려가 있다고 생각될 때 이 요청을 보낼 수 있다.
  • 410: Gone
    • 404와 비슷함. 서버가 한때 그 리소스를 갖고 있었다는 점이 다르다.
  • 411: Length Required
    • 서버가 요청 메시지에 Content-Length 헤더가 있을 것을 요구할 때 사용한다.
  • 412: Precondition Failed
    • 조건부 요청을 했는데 그 중 하나가 실패했을 때 사용한다.
  • 413: Request Entity Too Large
    • 서버가 처리하고자 하는 한계를 넘은 크기의 요청을 클라이언트가 보냈을 때 사용한다.
  • 414: Request URI Too Long
    • 서버가 처리하고자 하는 한계를 넘은 길이의 요청 URL이 포함된 요청을 클라이언트가 보냈을 때 사용한다.
  • 415: Unsupported Media Type
    • 서버가 이해, 지원하지 못하는 유형의 엔티티를 클라이언트가 보냈을 때 사용한다.
  • 416: Requested Range Not Satisfiable
    • 리소스의 특정 범위를 요청했는데, 그 범위가 잘못되었을때 사용한다.
  • 417: Expectation Failed
    • 요청에 포함된 Expect 요청 헤더에 서버가 만족시킬 수 없는 기대가 담겨있는 경우 사용한다.

500-599: 서버 에러 상태 코드

  • 500: Internal Server Error
    • 서버가 요청을 처리할 수 없는 에러를 만났을 때 사용한다.
  • 501: Not Implemented
    • 서버의 능력을 넘는 요청을 했을 때 사용한다.
  • 502: Bad Gateway
    • 프록시나 게이트웨이처럼 행동하는 서버가 그 요청 응답 연쇄에 있는 다음 링크로부터 가짜 응답에 맞닥뜨렸을 때 사용한다.
  • 503: Service Unavailable
    • 현재는 서버가 요청을 처리해줄 수 없지만 나중에는 가능함을 의미하고자 할 때 사용하낟.
  • 504: Gateway Timeout
    • 408과 비슷함. 다른 서버에게 요청을 보내고 응답을 기다리다 타임아웃이 발생한 게이트웨이나 프록시에서 온 응답이라는점이 다르다.
  • 505: HTTP Version Not Supported
    • 서버가 지원하지 않는 버전의 프로토콜로 된 요청을 받았을 때 사용한다.

3-5. 헤더

  • 헤더와 메서드는 클라이언트와 서버가 무엇을 하는지 결정하기 위해 함께 사용된다.

일반 헤더

  • 클라이언트, 서버 양쪽 모두 사용 가능
  • 다양한 목적으로 사용됨.
  • Connection: 클라이언트와 서버가 요청/응답 연결에 대한 옵션을 정할 수 있게 해준다.
  • Date: 메시지가 언제 만들어졌는지에 대한 날짜와 시간
  • MIME-Version: 발송자가 사용한 MIME 버전
  • Trailer chunked transfer: 인코딩으로 인코딩된 메시지의 끝 부분에 위치한 헤더들의 목록을 나열
  • Transfer-Encoding: 어떤 인코딩이 적용되었는지
  • Upgrade: 발송자가 업그레이드하길 원하는 새 버전이나 프로토콜
  • Via: 어떤 중개자를 거쳐 왔는지

일반 캐시 헤더

  • Cache-Control: 메시지와 함께 캐시 지시자를 전달하기 위해
  • Pragma: 메시지와 함께 지시자를 전달하는 또 다른 방법, 캐시에 국한되지 않음.

요청 헤더

  • 요청 메시지를 위한 헤더
  • 서버에게 받고자 하는 데이터 타입이 무엇인지와 같은 부가정보를 제공한다.
  • Cliet-IP: 실행된 컴퓨터의 IP
  • From: 사용자의 메일 주소
  • Host: 서버의 호스트 명과 포트
  • Refere: 현재의 요청 URI가 들어있던 문서의 URL
  • UA-Color: 디스플레이의 색상 능력에 대한 정보
  • UA-CPU: CPU의 종류나 제조사
  • UA-Disp: 디스플레이 능력에 대한 정보
  • UA-OS: 운영체제의 이름과 버전
  • UA-Pixels: 디스플레이에 대한 픽셀 정보
  • User-Agent: 요청을 보낸 애플리케이션의 이름

Accep 관련 헤더

  • 무엇을 원하고 무엇을 할 수 있는지, 원치 않는 것은 무엇인지에 대한 정보
  • Accept: 서버가 보내도 되는 미디어 종류
  • Accept-Charset: 서버가 보내도 되는 문자 집합
  • Accept-Encoding: 서버가 보내도 되는 인코딩
  • Accept-Language: 서버가 보내도 되는 언어
  • TE: 서버가 보내도 되는 확장 전송 코딩

조건부 요청 헤더

  • 요청에 제약을 넣을때 사용함.
  • Expect: 요청에 필요한 서버의 행동을 열거할 수 있게 해준다.
  • If-Match: 문서의 엔티티 태그가 주어진 엔티티 태그와 일치하는 경우에만 문서를 가져온다.
  • If-Modified-Since: 주어진 날짜 이후에 리소스가 변경되지 않았다면 요청을 제한한다.
  • If-None-Match: 문서의 엔티티 태그가 주어진 엔티티 태그와 일치하지 않는 경우에만 문서를 가져온다.
  • If-Range: 문서의 특정 범위에 대한 요청을 할 수 있게 해준다.
  • If-Unmodified-Since: 주어진 날짜 이후에 리소스가 변경되었다면 요청을 제한한다.
  • Range: 서버가 범위 요청 지원시, 리소스에 대한 특정 범위 요청

요청 보안 헤더

  • 요청하는 클라이언트가 어느 정도의 리소스에 접근하기 전에 자신을 인증하게 함으로써 트랜잭션을 약간 더 안전하게 만들고자 한다.
  • Authorization: 서버에게 제공하는 인증 그 자체에 대한 정보
  • Cookie: 서버에게 토큰을 전달할 때 사용
  • Cookie2: 요청자가 지원하는 쿠키의 버전을 알려줄 때 사용

프록시 요청 헤더

  • Max-Forwards: 요청이 원 서버로 향하는 과정에서 다른 프록시나 게이트웨이로 전달될 수 있는 최대 횟수
  • Proxy-Authorization: Authorization과 같으나 프록시에서 인증시 사용
  • Proxy-Connection: Connection과 같으나 프록시에서 인증시 사용

응답 헤더

  • 클라이언트에게 정보를 제공하기 위한 헤더
  • Age: 응답이 얼마나 오래됐는지
  • Public: 서버가 특정 리소스에 대해 지원하는 요청 메서드의 목록
  • Retry-After: 리소스가 사용 불가능한 상태일 때, 언제 가능해지는지
  • Server: 서버 애플리케이션의 이름과 버전
  • Title: HTML 문서에서 주어진 것과 같은 제목
  • Warning: 사유 구절에 있는 것보다 더 자세한 경고 메시지

협상 헤더

  • Accept-Ranges: 서버가 자원에 대해 받아들일 수 있는 범위의 형태
  • Vary: 서버가 확인해 봐야 하고 그래서 응답에 영향을 줄 수 있는 헤더들의 목록

응답 보안 헤더

  • Proxy-Authenticate: 프록시에서 클라이언트로 보낸 인증요구 목록
  • Set-Cookie: 클라이언트 측에 토큰을 설정하기 위해서
  • Set-Cookie2: Set-Cookie와 비슷하게 RFC 2965로 정의된 쿠키
  • WWW-Authenticate: 서버에서 클라이언트로 보낸 인증요구 목록

엔티티 헤더

  • 엔티티 본문에 대한 헤더
  • Allow: 이 엔티티에 대해 수행될 수 있는 요청 메서드
  • Location: 엔티티가 실제로 어디에 위치하고 있는지 말해준다.

콘텐츠 헤더

  • Content-Base: 본문에서 사용된 상대 URL을 계산하기 위한 기저 URL
  • Content-Encoding: 본문에 적용된 인코딩
  • Content-Language: 본문 이해하는데 가장 적절한 언어
  • Content-Length: 본문 길이나 크기
  • Content-Location: 리소스 실제 위치
  • Content-MD5: MD5 체크섬
  • Content-Range: 이 엔티티가 해당하는 범위를 바이트 단위로
  • Content-Type: 이 본문이 어떤 종류의 객체인지

엔티티 캐싱 헤더

  • ETage: 엔티티에 대한 엔티티 태그
  • Expires: 엔티티가 더 이상 유효하지 않아 원본을 받아와야 하는 일시
  • Last-Modified: 가장 최근 엔티티가 변경된 일시

확장 헤더

  • 아직 승인된 HTTP 명세에는 추가되지 않은 비표준 헤더

' > misc' 카테고리의 다른 글

안정 해시 설계  (2) 2022.06.21
처리율 제한 장치의 설계  (3) 2022.06.19
2장. URL과 리소스  (0) 2022.04.25
1장. HTTP 개관  (0) 2022.04.24
HTTP 완벽 가이드 책 샀다.  (2) 2022.02.10