본문 바로가기

프로그래밍/개발

HTTP Response, Request에 관하여

HTTP는 HTML 문서와 같은 리소스들을 가져올 수 있도록 해주는 프로토콜이다.

 

정말 자세한 내용은

https://www3.ntu.edu.sg/home/ehchua/programming/webprogramming/HTTP_Basics.html

 

In Introduction to HTTP Basics

HTTP (HyperText Transfer Protocol) Basics Introduction The WEB Internet (or The Web) is a massive distributed client/server information system as depicted in the following diagram. Many applications are running concurrently over the Web, such as web browsi

www3.ntu.edu.sg

해당 문서에 나와있으니 한번 정독해보도록하자.

 

WAS를 이어서 구현하고 있는데,

내가 구현하기위해서 필요한 내용은 HTTP Request와 HTTP Response가 어떤식으로 구성 되 어있는 지였고 이를 gpt에게 물어보았다.

 

HTTP Request Get요청 예시

GET /index.html HTTP/1.1
Host: www.example.com
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64)
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate, br
Connection: keep-alive

 

HTTP Response 예시

HTTP/1.1 200 OK
Date: Mon, 23 May 2022 22:38:34 GMT
Server: Apache/2.4.1 (Unix)
Last-Modified: Wed, 22 Jul 2020 19:15:56 GMT
Content-Type: text/html
Content-Length: 1234

<html>
<head>
    <title>An Example Page</title>
</head>
<body>
    Hello World, this is a very simple HTML document.
</body>
</html>

 

첫 요구사항인 index.html을 브라우저로 반환하기를 구현해야하는 내가 원하는 내용들이었다.

그외에 다른 사이트들을 인터넷 분석도구(F12)로 네트워크 부분에서 읽어오는 요청들을 보니 비슷한 형태를 띄고 있음을 알 수 있었다. 그리고 검색하고 공부한 결과 몇가지 사실을 알 수 있었다.

 

1. Request와 Response는 Header, Body 두개로 이루어져있고 빈 줄로 이를 분리한다.

2. Request의 경우에 첫줄은 MethodRequest, TargetHttp, HttpVersion 3가지로 구성되어있고 다음 줄은 Header로 구성된다.

3. Response도 마찬가지로 HttpVersion, StatusCode, StatusText 3가지로 구성되어있고 다음 줄은 Header로 구성된다.

 

초기 설계

여기까지 보고 내가 설계한 내용은 다음과 같았다.

 

1. 기존의 RequestHandler가 socket으로 연결하고 InputStream으로 Http요청을 가져온다.

2. Request객체에서 이를 파싱하여 첫 줄은 해당하는 변수 이름에 넣어주고 나머지 헤더, 바디의 경우 HashMap형식으로 넣어준다.

3. Response객체가 Request객체를 참고하여 HashMap에 반환할 헤더, 바디를 넣는다.

4. 다시 돌아와 RequestHandler에서 DataoutputStream으로 Http요청을 보낸다.

 

그림으로 보면 다음과 같다.

미리 생각했던 부분으로는 Response의 상태코드는 정해진 값이니 Enum형으로 설정해 뒀었다. 하지만, 당장에도 index.html을 반환하는것을 구현하는 것에 문제가 있다. Response객체가 Body를 HashMap형식으로 가지고 있다는 것이었다. 내가 생각한 일반적인 요청이 /user/get 과 같은 json을 반환하는 api라고 생각하여 그렇게 설계했기 때문이다. 따라서, 요청마다 이를 처리해줄 녀석이 필요하다.

 

1. /index.html : index.html이 반환값으로 필요함.

2. /user/get : json형태가 반환값으로 필요함.

설계 수정

우선 위의 두가지 경우를 처리하기위해 RequestHandler를 만들어줬다. 그런데 이 RequestHandler는 WebServer에서 전달받는 클래스와 이름이 같다. 그래서 이름부터 바꿔줬다. 변경된 사항들은 아래와 같다.

1. 확장자를 보고 MIME 타입(ENUM형)을 저장한다.

2. 기존에 Response Body가 HashMap이었는데 이를 byte[] 형태로 변환하여 html, css 등의 데이터들을 처리 가능하고 Json의 경우에도 직렬화하여 처리 가능하게 했다.

3. RequestHandler에서는 api요청일 경우 

private final Map<String, Consumer<Request>> routeHandlers= new HashMap<>();

 

이런형태로 router를 구현하여 요청사항에 맞는 함수를 실행한다. 이 부분에 해당하는 내용은 Step2 Get요청 처리하는 부분을 위해서 만들어 졌다.

4. ResponseHandler에서 html, css등 반환값이 필요한 데이터의 경우 MIME타입을 확인하고 html과 css를 저장하는곳이 template폴더와 static폴더로 다르기 때문에 이 부분을 처리해 준다.

 

해당 내용들을 적용한 구조가 다음과 같다.

 

 

Step1 index.html 브라우저에 전달

Step2 Get요청 처리

Step3 다양한 MIME 타입 적용 css, js

 

이 모든 내용들이 위의 구조로 일단은 잘 돌아가고 있다.

다음 Step이 Post요청인데, 이 부분도 역시 RequestHandler에서 처리 가능 할듯 하다.

 

후기

제일 막막했던 부분이 사실 첫날 이었다. 정해진 요구사항은 있었지만, Get, Post 등의 요청이 있는 것도 알고 정적인 콘텐츠, api들이 있는 것은 알지만 어떻게 동작하는 지를 몰랐기 때문에 어떻게 해야 이러한 것들을 적용 할 수 있을 까 라는 생각으로 공부를 하였고 구조 역시 간단한 요구사항들을 따르되 확장성 있는 코드를 작성하자 라는 점에서 아직 까지는 괜찮은 구조 인것 같다.

'프로그래밍 > 개발' 카테고리의 다른 글

if문을 줄이는 방향에 대한 고찰  (0) 2024.01.23
자바의 멀티스레드  (0) 2024.01.22
몰랐던 Git에 관한 이야기  (0) 2024.01.21
WAS란 무엇인가?  (0) 2024.01.21
Java 문법 Integer, int 그리고 final  (0) 2023.10.23