웹 서버, WAS, 서블릿과 쓰레드 풀

이건희·2023년 8월 7일
1

스프링 강의를 듣던 도중 웹 서버와 WAS, 그리고 WAS에서 지원하는 스레드 관리 등을 배우게 되었고 이해 대해 정리해보려 한다.


Web Server

  • HTTP 기반으로 동작

  • 정적 리소스 제공, 기타 부가 기능 제공

  • 정적(파일) HTML, CSS, JS, 이미지, 영상 등

즉, Web Server는 요청이 오면 정적 리소스 파일들을 제공하는 역할을 한다. 정적 리소스 파일을 제공한다는 말은, 별도의 로직을 처리하지 않고 미리 저장된 파일들을 제공하기만 한다는 것이다.


WAS(Web Application Server)

  • HTTP 기반으로 동작

  • 웹 서버 기능 포함(정적 리소스 제공)

  • 프로그램 코드를 실행해서 어플리케이션 로직 실행

    • 동적 HTML, HTTP API(JSON)
    • 서블릿, JSP, 스프링 MVC
  • 예) 톰캣(Tomcat), Jetty, Undertow

WAS는 요청이 들어오면 어플리케이션 로직을 실행하여 응답을 제공한다.

강의에서는 둘의 경계가 모호하다고 한다. 웹 서버도 프로그램을 실행하는 기능을 포함하기도 하고 WAS도 웹 서버의 기능을 제공하기 때문이다. WAS는 어플리케이션 코드를 실행하는데 더 특화 되어있다. 자바에서는 서블릿 컨테이너 기능을 제공하면 WAS라 칭한다.


웹 시스템 구성

WAS가 웹 서버의 기능도 제공하니까 아래처럼 WAS만으로 웹 시스템을 구성하면 되지 않을까?

WAS만으로 웹 시스템 구성 시 다음과 같은 문제점들이 발생할 수 있다.

  • WAS가 너무 많은 역할을 담당하여 서버 과부하 우려

  • WAS는 웹 서버에 비해 잘 죽음

  • 가장 비싼 어플리케이션 로직이 정적 리소스 때문에 수행이 어려울 수 있음

  • WAS 장애 시 오류 화면 노출 불가능

그래서 보통 아래와 같이 웹 시스템을 구성한다.

위와 같이 구성 시 다음과 같은 이점들이 있다.

  • 정적 리소스는 웹 서버가, 동적인 처리는 WAS 담당

  • 분업하여 요청을 처리해 효율적인 리소스 관리 가능

  • 정적 리소스가 많이 사용되면 웹 서버 증설, 동적 리소스가 많이 사용되면 WAS를 증설하면 됨

  • 웹 서버는 잘 죽지 않으므로 WAS 장애 시 오류 화면 제공 가능


서블릿

HTTP 요청과 응답을 위해선 많은 일들이 필요하다. 소켓 연결, HTTP 메세지 파싱, 어떤 메소드 사용 했는지, 메세지 바디 파싱, 응답 메세지 생성 등등등...

이를 개발자가 모두 다 하기에는 번거롭고 반복적이다. 따라서 서블릿은 비즈니스 로직 제외 HTTP 요청, 응답에 필요한 대부분의 것들을 해준다.

아래 그림에서 줄이 쳐져 있는 것은 서블릿이 해주는 일이다.

서블릿은 다음과 같은 흐름으로 작동한다.

  • HTTP 요청 시, WAS는 Request, Response 객체를 만들어 서블릿 객체 호출

  • 개발자는 Request 객체에서 HTTP 요청 정보를 편리하게 꺼내서 사용

  • 개발자는 Response 객체에서 HTTP 응답 정보를 편하게 입력

  • WAS는 Response 객체에 담겨 있는 내용으로 HTTP 응답 정보 생성

서블릿 컨테이너

이와 같이 WAS는 대부분 서블릿을 지원하는데, 톰캣처럼 서블릿을 지원하는 WAS를 서블릿 컨테이너라고 한다.

서블릿 컨테이너는 서블릿 객체 생성, 초기화, 호출, 종료를 관리한다.

서블릿 컨테이너는 객체를 싱글톤으로 관리한다.

또한 동시 요청을 위한 멀티 쓰레드을 지원한다.


동시 요청 - 멀티 쓰레드

  • 서블릿 객체를 호출하는 것은 쓰레드이다.

  • 쓰레드는 어플리케이션 코드를 하나하나 순차적으로 실행한다.

  • 쓰레드는 한번의 하나의 코드 라인만 수행한다.

  • 동시 처리가 필요하면 쓰레드를 추가로 생성해야 한다.

동시 처리가 필요할 시 쓰레드를 추가로 생성하면 된다고 하였는데, 요청 시마다 쓰레드를 계속 생성하면 되는건가?

정답은 아니다. 오청 시마다 쓰레드를 생성할 시 다음과 같은 장단점들이 있다.

  • 장점
    • 동시 요청 처리 가능
    • 리소스(CPU, 메모리) 허용 치 까지 생성 가능
    • 하나의 쓰레드가 지연 되어도, 나머지 쓰레드 정상 작동
  • 단점
    • 쓰레드 생성 비용은 매우 비싸다 !
    • 고객 요청 시마다 쓰레드 생성 시 응답 속도가 느려진다.
    • 쓰레드 생성 제한이 없어 요청이 너무 많을 시 CPU, 메모리 임계점을 넘어 서버가 죽을 수 있다.

위와 같은 단점들이 있기에, 쓰레드 풀이란 개념이 사용된다.

쓰레드 풀이란 쓰레드가 미리 생성되어 담겨있는 곳이다. 따라서 요청이 오면, 이미 생성되어 있는 쓰레드를 쓰레드 풀에서 꺼내서 사용하고 반납한다.

또한 다음과 같은 특징들이 있다.

  • 쓰레드 풀에서 생성 가능한 쓰레드 개수의 최대치 설정 가능

  • 최대 쓰레드 개수를 넘길 시, 특정 숫자만큼 대기 또는 거절하도록 설정 가능

  • 쓰레드가 미리 생성 되어 있으므로 쓰레드 생성 종료 비용 절약 : 응답 시간이 빠르다.

  • 생성 가능한 쓰레드의 개수가 정해져 있으므로 많은 요청이 들어와도 안전하다.

서버 관리 측면에서 중요하게 생각되어야 하는 것이 쓰레드 풀의 최대 쓰레드(Max Thread)이다.

값이 너무 낮을 시, CPU는 여유롭지만 동시 요청은 지연, 너무 높을 시 CPU 임계점 초과로 서버 다운 같은 상황이 발생할 수 있다.

따라서 어플리케이션 로직의 복잡도, CPU, 메모리, IO 리소스 상황에 따라 성능 테스트를 진행하며 적절한 최대 쓰레드 수를 찾는 것이 개발자의 업무라고 할 수 있다.


출처 : 인프런 영한 스프링 MVC 강의 1편

profile
백엔드 개발자가 되겠어요

4개의 댓글

comment-user-thumbnail
2023년 8월 7일

좋은 글 감사합니다 :)

1개의 답글
comment-user-thumbnail
2023년 8월 7일

유익한 내용 감사합니다!

1개의 답글