서블릿(Servlet)이란?
1. 서블릿이란 무엇인가?
서블릿은 동적 웹 페이지를 만들 때 사용되는 자바 기반의 웹 애플리케이션 프로그래밍 기술입니다. 클라이언트의 요청을 처리하고 응답을 생성하는 자바 클래스입니다. Servlet은 일반적으로 HTTP 프로토콜을 기반으로 작동하며, 클라이언트의 요청을 받아들여 처리하고, 데이터베이스 연동, 파일 처리 등의 작업을 수행하여 동적인 웹 페이지를 생성하거나 RESTful API와 같은 서비스를 제공하는 데 사용됩니다.
참조: Tomcat-서블릿Servlet이란
Servlet은 주로 웹 애플리케이션의 백엔드 로직을 처리하는 데 활용되며, HTTP 요청에 대한 응답으로 HTML 페이지, JSON, XML 등의 데이터를 생성할 수 있습니다. Servlet은 자바 언어의 기능을 활용하여 유연하고 강력한 서버 측 로직을 구현할 수 있는 장점을 가지고 있습니다.
2. Servlet의 특징
- 동적인 콘텐츠 생성: 클라이언트의 Request에 동적으로 작동하는 웹 어플리케이션 컴포넌트입니다. 클라이언트의 요청을 받아들여 처리하고, 데이터베이스 쿼리, 파일 처리, 비즈니스 로직 실행 등을 통해 동적으로 웹 페이지나 다양한 데이터 형식을 생성하여 응답합니다.
- 플랫폼 독립성: 자바 기반으로 작성되어 있기 때문에, Servlet은 플랫폼 독립성을 제공합니다. Servlet 코드는 한 번 작성되면 서버 환경이 달라지더라도 동일하게 작동할 수 있습니다.
- 스레드 지원 및 멀티스레딩: 서블릿 컨테이너는 여러 클라이언트 요청을 동시에 처리하기 위해 멀티스레드를 사용합니다. 각 요청에 대해 별도의 스레드가 할당되어 독립적으로 실행됩니다.
- 확장성: Servlet은 기능을 확장하기 쉽습니다. Servlet은 자바 EE(Java EE)의 다양한 API와 함께 사용될 수 있으며, 필요에 따라 다양한 라이브러리나 프레임워크와 통합하여 기능을 확장할 수 있습니다.
- HTTP 프로토콜 지원: 주로 HTTP 요청을 처리하고 응답을 생성하는 데 사용됩니다. javax.servlet.http.HttpServlet 클래스를 상속 받습니다.
이러한 특징들로 인해 Servlet은 웹 애플리케이션 개발에서 핵심적인 역할을 수행하고 있으며, 동적인 웹 콘텐츠 생성 및 서버 측 로직 처리에 널리 사용됩니다.
3. 동작 과정
클라이언트의 HTTP 웹 서버 요청은 HTML에서 Servlet으로 전달되며, 톰켓을 운영하는 WAS에서 작동합니다. Servlet은 데이터베이스에서 검색된 정보를 사용하여, HTML 페이지로 응답하게 되어 클라이언트에게 전송됩니다.
4. 서블릿 컨테이너(Servlet Container)
서블릿 컨테이너는 서블릿 클래스의 규칙을 따르는 서블릿을 관리하는 환경입니다.
클라이언트 요청 시 HttpServletRequest와 HttpServletResponse 객체를 생성하여, HTTP 요청의 유형(GET 또는 POST 등)에 따라 동적인 페이지를 생성하고 이에 대한 응답을 생성하여 클라이언트에게 반환합니다. 이를 통해 Servlet Container는 서블릿의 실행, 생명주기 관리, 요청 처리 및 응답 생성을 담당합니다.
대표적인 Servlet Container는 Apache Tomcat, Jetty, WildFly(JBoss), IBM WebSphere 등이 있으며, 이들은 자체적인 구현체와 기능을 가지고 있으며 서블릿 스펙에 따라 동작합니다. Servlet Container는 웹 애플리케이션을 실행하고 관리하여 동적인 콘텐츠 생성 및 클라이언트 요청에 응답하는 역할을 합니다.
4.1 웹서버와의 통신 지원
Servlet은 웹 서버와의 통신을 지원하는 기술입니다. 이를 통해 클라이언트의 HTTP 요청을 받아들이고, 요청에 따른 처리를 수행하여 동적인 웹 콘텐츠를 생성하며, 이를 다시 클라이언트에 응답합니다. Servlet은 주로 HTTP 프로토콜을 기반으로 동작하여 클라이언트의 요청을 처리하고 적절한 응답을 생성하여 웹 서버를 통해 클라이언트에 전달하는 역할을 수행합니다.
4.2 서블릿 생명주기 관리
서블릿 생명주기는 서블릿의 생성부터 소멸까지의 과정을 의미합니다. 서블릿 컨테이너는 이러한 생명주기를 관리하며, 다음과 같은 단계로 나뉩니다
- 로딩(Loading): Servlet이 처음 요청되거나 웹 애플리케이션이 시작될 때, Servlet 컨테이너는 해당 서블릿 클래스를 로딩합니다.
- 인스턴스화(Instantiation): 로딩된 Servlet 클래스로부터 Servlet의 인스턴스를 생성합니다. 이 단계에서 init() 메서드가 호출되어 초기화 작업을 수행할 수 있습니다.
- 서비스(Service): 클라이언트의 요청이 들어올 때마다 Servlet 컨테이너는 해당 Servlet의 service() 메서드를 호출하여 요청을 처리합니다. service() 메서드는 요청의 HTTP 메서드(GET, POST 등)에 따라 적절한 메서드(doGet(), doPost() 등)를 호출하고, 요청을 처리합니다.
- 소멸(Destruction): Servlet이 더 이상 필요하지 않을 때(웹 애플리케이션이 종료되거나 Servlet을 제거할 때), Servlet 컨테이너는 해당 서블릿의 destroy() 메서드를 호출하여 마무리 작업을 수행합니다. 여기서는 리소스 해제나 정리 작업을 수행할 수 있습니다.
이러한 생명주기를 통해 Servlet은 요청을 처리하고 응답을 생성하며, Servlet Container는 이러한 과정을 관리하여 Servlet의 초기화, 실행, 종료 등을 효과적으로 관리합니다.
4.3 멀티스레드 지원 및 관리
Servlet Container는 멀티쓰레드를 지원하고 관리합니다. 다수의 클라이언트 요청이 동시에 발생할 수 있기 때문에, 이를 효율적으로 처리하기 위해 멀티쓰레드를 사용합니다.
- 요청당 쓰레드 생성: 각 클라이언트 요청마다 별도의 쓰레드를 생성하여 요청을 처리합니다. 이렇게 하면 여러 요청이 동시에 처리될 수 있습니다.
- 쓰레드 풀 관리: 일정한 개수의 쓰레드 풀을 유지하여 요청이 발생하면 이 풀에서 쓰레드를 가져와 처리합니다. 쓰레드 풀은 쓰레드의 재사용을 통해 쓰레드 생성 및 소멸에 따른 오버헤드를 줄입니다.
- 동기화(Synchronization): 멀티쓰레드 환경에서 여러 쓰레드가 공유하는 자원에 대한 접근을 제어하기 위해 동기화 메커니즘을 사용합니다. 이를 통해 쓰레드 간의 충돌을 방지하고 안전한 자원 접근을 보장합니다.
- 쓰레드 스케줄링: 여러 쓰레드가 동작하는 경우, 쓰레드 스케줄링을 통해 적절한 우선순위를 부여하여 자원을 효율적으로 활용합니다.
서블릿 컨테이너는 이러한 멀티쓰레드 관리를 통해 다수의 클라이언트 요청을 동시에 처리하고, 각 요청을 적절히 분배하여 안전하고 효율적으로 Servlet을 실행합니다. 이를 통해 다중 사용자 환경에서 안정적인 서비스를 제공할 수 있습니다.
4.4 선언적인 보안 관리
서블릿 콘테이너를 사용하면 보안에 관련된 내용을 Servlet 또는 자바 클래스에 구현해 놓을 필요가 없습니다. web.xml 파일(XML 배포 서술자 역할을 하는 파일)에서 선언적 보안을 구현할수 있습니다.
- : 보안 제약 조건을 지정합니다. 이를 통해 특정 URL 패턴에 대한 보안 규칙을 설정할 수 있습니다. 예를 들어, 특정 페이지에 대한 접근을 인증된 사용자에게만 허용하도록 설정할 수 있습니다.
- : 인증이 필요한 리소스에 접근할 때 사용자에게 로그인 페이지를 제공하기 위한 설정을 담고 있습니다. 보안 제약이 적용된 페이지에 접근할 때 사용자 인증을 수행할 로그인 폼을 지정합니다.
- : 역할을 정의하고, 이러한 역할을 가진 사용자가 특정 보안 규칙에 접근할 수 있는지를 정의합니다. 예를 들어, “admin”이라는 역할을 정의하고 특정 페이지에 admin 역할을 가진 사용자만 접근할 수 있도록 설정할 수 있습니다.
선언적인 보안 관리를 통해 개발자는 보안 규칙을 직접 코드에 구현(자바 소스 코드 수정 후 컴파일 방식 등)하는 것이 아니라 XML 기반의 설정을 통해 보안 요구사항을 관리할 수 있습니다.