들어가며

취업을 준비하는 많은 예비 개발자들이 Web ServerWeb Application Server의 차이점과 특징에 대해 공부하곤 한다.

나 역시 Web Server정적 페이지를 처리하기 위한 서버 이며 Web Application Server동적 페이지를 처리하기 위한 어플리케이션 서버 라고 외우고 면접을 보곤 했다.

그리고 신입 개발자가 된 후론 Web Application Server에 대하여 딱히 고민해본적이 없다. 단순히 자바 웹 어플리케이션의 컴포넌트인 서블릿들의 생명 주기를 관리하고 클라이언트의 요청에 따라 적절한 서블릿을 호출(init, service 등)하는 미들웨어 프로그램정도로 외웠을 뿐이다.

그리고 이런 얕고 부정확한 지식은 실무를 하는데 충분하지 못했다. 당장 내가 속한 팀에서 개발한 웹 어플리케이션 솔루션은 내장 톰캣을 이용하여 실행되는 중이었고 이 솔루션을 배포할 회원사는 JEUS를 사용한다.

윗 선임들의 여러 조언을 들었지만 톰캣JEUS의 차이를 알지 못하는, Web Application Server에 대해 제대로 알지 못하는 나로서는 소 귀에 경 읽기였다.

부끄러움을 무릅쓰고 약 2시간에 걸쳐 공부한 내용을 옮겨보려 한다.


Tomcat은 Web Application Server가 아니다?

몇몇 자료에서는 엄밀히 따지면 톰캣은 WAS가 아니다 라고 말한다.

그 이유인 즉 WAS를 충족하기 위해서는 JAVA EE(Java Enterprise Edition) 기술 스펙을 충족해야 하지만(구현해야 하지만) 톰캣JAVA EE 기술 스펙 중 JAVA SE에만 해당하는, 즉 서블릿/JSP 엔진을 구현Web Container라는 것이다.

만일 엄격한 WAS가 되기 위해서는 Web Container 구현 뿐 아니라 EJB Container의 구현까지 충족해야 한다고 한다.


Tomcat의 구성 요소

현재 JSP는 레거시의 영역에 들어선지 꽤 지났지만 일반적으로 Tomcat의 구성 요소를 정의할 때에는 크게 3가지의 컴포넌트로 구분한다.

  1. Coyote : HTTP 컴포넌트로 구성된다. 톰캣에 TCP를 통한 프로토콜을 지원한다.

  2. Catalina : 서블릿 컨테이너(웹 컨테이너)로써 자바 서블릿을 호스팅하는 환경이다.

  3. Jasper : 톰캣의 JSP 엔진으로써 JSP 최초 요청 및 변경 시 Servlet으로 변경 및 컴파일을 한다. (Spring boot 내장 톰캣에는 JSP 엔진이 빠져있는걸로 알고있다.)


여기까지 살펴봤을 때 TomcatJAVA SE 기술 표준에 따라 Web Container(미들웨어 프로그램)을 구현한 서버임을 알 수 있다.

그리고 개발자는 자바 웹 어플리케이션을 개발 및 Tomcat에 배포하면 Tomcat 실행 시 자체 설정 파일과 자바 웹 어플리케이션의 docBase를 참고하여 Web Container를 구동하고 클라이언트의 요청을 기술 표준에 따라 구현된 멀티스레딩, 네트워킹, 분산 처리 등의 과정을 거쳐 Web Container는 웹 어플리케이션의 서블릿들을 초기화, 실행, 소멸시킨다.


톰캣의 구조 (번역)

톰캣은 자바 웹 어플리케이션을 개발할 때 가장 자주 접하는 서버 컨테이너입니다. 그리고 톰캣은 서블릿 컨테이너이자 웹 어플리케이션 서버입니다.

Tomcat은 안정성과 경량성을 추구합니다. 그리고 톰캣이 가볍고 안정적이라는 사실은 많은 개발자들이 동의하는 사실입니다.

톰캣은 자바 웹 개발자들에게 있어 양질의 배울것들을 제공합니다. 만일 여러분이 톰캣의 디자인 원칙을 이해한다면 자바 웹 개발이 더이상 여러분들에게 블랙박스와같이 비밀스럽지 않을겁니다.

이 문서는 주로 톰캣의 내부 시스템 구조에 대해서 설명합니다.

앞서 말했듯이 톰캣은 WEB Server + Servlet Container이므로 네트워크 연결서블릿 관리(생명주기)를 처리합니다.

따라서 톰캣은 외부 네트워크 연결 처리를 위한 컴포넌트(커넥터)내부 서블릿 처리를 위한 컴포넌트(컨테이너)라는 두 가지 핵심 구성 요소를 갖고 디자인되었습니다.

위 사진에서 볼 수 있듯이 톰캣은 Server로 표현할 수 있습니다. 그리고 이 톰캣 서버는 다수의 Service를 갖고 있습니다.

톰캣의 기본 Service는 바로 Catalina이며 이 Service(Catalina)는 여러 Connector를 가질 수 있습니다. 왜냐하면 톰캣HTTP/1.1, HTTP/2, AJP 등 다양한 네트워크 프로토콜을 지원하기 때문입니다.

또한 하나의 Service(기본으로 Catalina)는 하나의 Container 또는 외부 Container를 가질 수 있습니다.

Engine으로 감싸져있는 레이어는 Connector들의 request와 response를 다룹니다(handles)

Connector들은 ServletRequest와 ServletReponse 객체들을 이용하여 컨테이너들과 통신합니다.

여기서 Connector가 다수라는 이야기는 클라이언트의 요청이 다수 들어오는 멀티 스레딩 방식을 이야기하는 것이 아니라 여러 HTTP 프로토콜 방식을 지원하는 것이라고 보면 되겠습니다.

아래의 톰캣 구조 설정 파일인 server.xml 파일을 보시면 더 이해가 잘 되실겁니다.

<Server port="8005" shutdown="SHUTDOWN">

  <Service name="Catalina">

    <Connector connectionTimeout="20000" port="8080" protocol="HTTP/1.1" redirectPort="8443" URIEncoding="UTF-8"/>

    <Connector port="8009" protocol="AJP/1.3" redirectPort="8443"/>

    <Engine defaultHost="localhost" name="Catalina">
    
      <Host appBase="webapps" autoDeploy="true" name="localhost" unpackWARs="true">

        <Context docBase="handler-api" path="/handler" reloadable="true" source="org.eclipse.jst.jee.server:handler-api"/>
      </Host>
    </Engine>
  </Service>
</Server>

참고 및 출처

  • 오브젝트