CS(computer science)/Backend Roadmap

1. How does the internet work? & 2. What is HTTP?

ebang 2023. 12. 6. 01:32
반응형

1. How does the internet work?

2. What is HTTP?

HTTP는 TCP/IP 기반의 애플리케이션 레이어 통신 프로토콜입니다.
클라이언트와 서버간의 통신방식을 규정합니다.
content가 어떻게 요청되었는지와 어떻게 전달될 것인지를 정의합니다.

실제로 어떻게 request, respond를 받는지는 TCP/IP에 의존합니다.
TCP를 사용하는 경우 기본적으로 80포트를 사용하며, HTTPS 는 443 포트를 사용합니다.

HTTP/0.9 - The One Liner

  • get method 만 있던 시절의 프로토콜
  • 헤더가 없었습니다.
  • 응답은 HTML

HTTP/1.0 - 1996

  • 응답의 종류가 다양해졌습니다.
    • HTML 외의 다른 image, videos 등
  • method가 다양해졌습니다.
    • POST, HEAD
  • 다양해진 내용과 메소드로 인해 header가 등장했습니다.
  • 응답을 구분하기 위해 상태코드가 추가되었습니다.
  • charset 지원이 가능해졌습니다.
  • multi-part types, authorization, caching, content encoding 등이 가능해졌습니다.
  • 헤더는 여전히 ASCII 코드였지만, 응답에 다양한 종류가 포함될 수 있어짐에 따라, HTTP에서 Hyper Text라는 말이 무색해졌다.
  • 단점이 존재합니다.
    • 요청 하나당 여러개의 request를 보낼 수 없습니다.
    • 요청사항이 있을 때마다 새로운 TCP 연결을 맺어야하며, 응답을 받으면 연결이 끊어져 버립니다.
    • 한 웹사이트를 방문해서 10개의 이미지, 5개의 javascript file, 5개의 style sheet를 받아와 로드되기 위해서는 20개의 연결이 필요합니다.
      • TCP는 3-way handshake를 사용하기 때문에 성능상 페널티가 있습니다.

Three-way Handshake

Three-way handshake 는 TCP 연결을 맺은 후 클라이언트과 서버가 여러 패킷을 받아야 하는데, 연결 이전에 맺는 과정을 의미합니다.

  • SYN : 클라이언트가 랜덤 넘버x를 고른 후, server에 보냅니다.
  • SYN ACK : 서버는 받은 요청에 대해 새로운 랜덤 넘버 y와 x + 1로 이루어진 SYN ACK 메시지를 보냅니다.
  • ACK : 클라이언트는 받은 다음 y+1를 담아 ACK 메시지를 보냅니다.

three-way handshake가 이루어지고 나서는, 클라이언트와 서버 사이에 데이터 공유가 일어납니다. 클라이언트는 ACK 패킷을 보내자마자 바로 application data를 보내지만, 서버측에서는 응답을 보내기 위해서는 클라이언트가 보낸 ACK을 먼저 기다립니다.
TCP

HTTP/1.0 에서는 이 문제를 해결하기 위하여, Connection: keep-alive 라는 헤더를 추가하였습니다.
이 헤더의 의미는 다음과 같습니다.
“서버야, 연결을 끊지마. 다시 필요할 거야.”
하지만 전역적으로 지원되지는 않았고 문제는 여전히 존재했습니다.

  • 비연결성(connectionless)이라는 특징과는 별개로, HTTP stateless 프로토콜이기도 합니다.
  • 다시 말하면, 클라이언트에 대한 정보를 별도로 저장하지 않기 때문에, 클라이언트가 요청을 할 때마다 필요한 정보를 모두 담아서 요청을 해야만 합니다.
  • 이러한 문제로 인해, 매 요청마다 threeway handshake 로 인해 비용이 발생하는 것과 더불어 메시지의 내용도 중복된 것이 많아 대역폭 사용량이 많아지게 됩니다.

HTTP/1.1- 1997

  • HTTP/1.0 이 나온지 얼마 되지 않아 3년만에 HTTP/1.1 버전이 등장했습니다.

  • 새로운 HTTP method가 추가되었습니다 : PUT, PATCH, OPTIONS, DELETE

  • HTTP/1.0 에서는 필수가 아니던 host header가 필수사항이 되었습니다.

  • HTTP/1.0 에서는 하나의 연결 당 하나의 요청만 보내고, 이후에는 연결이 바로 끊겼기 때문에 지연 문제와 성능 저하가 심각했었습니다.

  • HTTP/1.1 에서는 지속적인 연결이 가능해졌습니다.

  • 다시 말해, 기본적으로 연결이 끊어지지 않으며, 클라이언트가 연결을 끊을 것을 요청해야 이루어집니다. 주로 이것은 헤더에 포함됩니다.

  • 파이프라이닝이 도입되었습니다.

  • 클라이언트가 서버의 응답을 기다리지 않고 여러 개의 요청을 보내는 것입니다.

  • 서버는 요청이 온 순서대로 응답하게 됩니다.

  • 하지만 클라이언트가 첫번째 응답이 오고 다운로드가 끝났으며 다음 응답에 대한 내용이 시작된다는 것은 어떻게 알 수 있을까요?

  • Content-Length 헤더를 통해, 클라이언트는 응답이 어디서 종료되었는지 알 수 있습니다.

  • 데이터가 동적이라서 Content-Length를 포함하지 못한다면 어떻게 될까요?

  • 하나의 요청에 대한 응답이 도착했다는 것을 알고 있어야만 다음 요청을 할 수 있거나, 다음 응답을 기다릴 수 있습니다. 그렇지 못한다면 지속적인 연결을 하는 이점이 사라지게 되죠.

  • 따라서 Content-Length를 사용하지 못하는 경우, Chunk-encoding 방식을 이용해서 content-Length를 생략할 수 있습니다.

  • 동적 컨텐츠를 전송할 때는 서버가 Content-Length를 알지 못하기 때문에, content를 조각 조각 나누어서 보내기 시작하고, chunk의 Content-Length를 추가해서 보내게 됩니다. 모든 청크가 보내지게 되면, 마지막에는 Content-Length 값이 0인 청크를 보내 끝임을 알리게 됩니다.

  • chunked-transfer임을 알리기 위해, 서버는 Transfer-Encoding: chunked 라는 헤더를 추가하게 됩니다.

  • HTTP/1.0 가 기본 인증만 있었던 반면, HTTP/1.1은 digest, proxy 인증을 가지고 있습니다.

  • 캐싱

  • Byte Ranges

  • Chracter sets

  • Language negotiation

  • Client cookies

  • HTTP/1.1에도 단점은 존재합니다.

  • 오늘날의 하나의 웹페이지는 30개의 연결을 수행해야합니다. 지속적인 연결을 사용함에도 불구하고, 왜 이렇게 많은 연결을 하는 걸까요?

  • 그 이유는 HTTP/1.1 은 언제든 하나의 대기상태인 연결만 가질 수 있기 때문입니다. 이것을 해결하기 위해, 파이프라이닝을 도입했으나, head-of-line blocking 문제로 인해 완전히 해결되지 못했습니다.

  • 시간이 오래걸리는 요청이 응답을 기다리고 있는 동안, 다른 요청을 block할 수 있습니다.

SPDY - 2009

구글은 웹을 더 빠르게 만들고 보안은 향상시키기 위해 몇가지 실험을 했습니다.

  • 대역폭이 계속 증가하게 된다면, 네트워크 성능은 초반에는 같이 증가하지만, 성능이 개선되지 않는 시점이 오게 됩니다. 하지만 지연은, 지연이 낮아지면 낮아질 수록 네트워크 성능이 좋아진다는 특징이 있습니다.
  • 이러한 특징에 기반하여 SPDY가 탄생하게 되었습니다: 지연을 낮추어 네트워크 성능을 올리는 것입니다.

HTTP/2 - 2015

  • content 전송에 있어 낮은 지연을 위해 디자인 되었습니다.
  • HTTP/1.1 버전과 비교하여 달라진 점은 다음과 같습니다.
    • 텍스트 형식이 아닌 이진 형식
    • multiplexing - 하나의 연결에서 여러개의 비동기 HTTP 요청
    • HPACK 을 사용한 header 압축
    • Server Push - 하나의 요청에 대한 여러개의 응답
    • 요청 우선순위화
    • 보안

image

  1. Binary Protocol
    • 읽을 수는 없게 되었지만, 파싱하기에 더 적합해졌습니다. HTTP/2의 주요 구성 요소는 프레임과 스트림입니다.
      Frames and Streams
  • HTTP 메시지들은 한 개 이상의 frame으로 구성되어 있습니다.

    • HEADERS frame : meta data를 저장합니다.
    • DATA frame : payload 를 저장합니다.
    • 기타 : RST_STREAM, SETTINGS, PRIORITY
  • 모든 HTTP//2 요청, 응답은 모두 유니크한 stream ID를 가지고 있으며 frame 여러개로 구성됩니다.

    • frame은 바이너리 데이터 조각에 지나지 않습니다.
    • frame이 모여서 하나의 Stream이 됩니다.
    • 각각의 frame은 자신이 속한 Stream을 구별하기 위해 stream id를 가지고 있습니다.
      • 클라이언트가 보내는 요청의 stream ID는 홀수 번호이고, 서버가 보내는 응답의 stream ID는 짝수번호라는 특징도 있습니다.
  • DATA, HEADERS frame 외에 설명할만한 frame에는 RST_FRAME 이 있습니다. 이 frame은 이제 클라이언트가 더이상 해당 stream이 필요하지 않다는 것을 의미합니다.

    • HTTP/1.1 에서 server가 요청을 읽어들이는 것을 중단할 방법은 연결을 끊는 방법밖에 없었던 것에 비하면 큰 변화입니다.
    • HTTP/2 에서는 연결이 끊어지지 않고도 stream을 중단할 수 있게 된 겁니다.
    1. Multiplexing
    • 요청, 응답에 frame과 stream 을 사용하며, 이진 데이터를 보내는 HTTP/2 에서는, TCP 연결이 생기고 나면 추가적인 연결없이 모든 stream이 하나의 연결에서 비동기적으로 보내지게 됩니다.
    • 따라서 서버도 비동기적으로 응답을 처리하게 됩니다. 이러한 문제는 HTTP/1.1 에 있었던 head-of-line 문제를 해결해줍니다.
      • 클라이언트가 응답을 대기중인 요청에 대해 더이상 block 되지 않기 때문입니다.
  1. Header Compression
  • stateless한 http 연결의 특징 상, 헤더에 언제나 중복 데이터가 많이 포함되어있었으며, 쿠키가 헤더 크기를 늘리기도 하여 대역폭 사용량이 증가되었던 문제가 있었습니다. 이를 해결하기 위해 헤더 압축이 도입되었습니다.
  • 헤더 압축에서는 값만 압축되고 헤더 테이블은 클라이언트, 서버에 대해 모두 유지 됩니다. 이후에 반복적인 헤더를 생략하고, 둘다에 의해서 유지되는 헤더 테이블을 사용해서 참조합니다.
  • 헤더의 내용 자체는 HTTP/1.1 과 큰 변화는 없습니다.
    • 달라진 헤더

:method:scheme:host and :path
```

  1. Server push
  • 클라이언트가 필요할 것임을 알고, 클라이언트가 요청하기도 전에 응답을 하는 것을 말합니다.
  • 브라우저가 웹 페이지를 로딩한다면, 브라우저는 모든 페이지를 파싱해서 서버로부터 몇가지 컨텐츠를 가져와야 한다는 것을 알고나면 그 다음에 필요한 요청들을 서버로 보냅니다.
  • server push는 클라이언트가 요청할 것들에 대해 미리 응답함으로써 해당 요청을 줄입니다.
  • PUSH_PROMISE 라고 불리는 frame을 통해서, 해당 메시지를 보내게 되며, 예측하게 된 stream의 stream id를 담아서 보냅니다.
  1. Request Prioritization
  • 클라이언트는 스트림에 우선순위를 부여할 수 있습니다.
  • HEADERS frame에 우선순위 정보를 넣을 숭 ㅣㅆ습니다.
  • 서버는 우선순위 정보가 없다면 비동기적으로 순서와 관계없이 요청을 처리하고, 우선순위가 정해져있다면 요청 프로세스에게 얼마나 많은 자원이 필요할지 결정합니다.
  1. Security
  • TLS와 같은 보안이 HTTP/2에서 필요할지 여부에 대해 많은 토론이 있었고, 결과적으로 의무적으로 하지는 않기로 하였습니다.
  • 하지만 대부분의 vendor들은 HTTP/2 를 TLS 위에서만 허용한다고 밝힙니다. 따라서 HTTP/2 에서 TLS는 중요한 부분이며, 주로 사용된다고 볼 수 있습니다.
반응형