Servlet container
tomcat 등 servlet을 관리하는 역할입니다. 초기화, 실행, 사용 등의 라이프사이클을 제어합니다.
서블릿 컨테이너가 서블릿을 실행하는 방법은 서블릿 생명주기와 관련있습니다.
최초 서블릿을 호출할 때 init 메소드를 호출합니다.
그 뒤 http method 에 따라서 doGet, doPost 등의 메소드가 호출됩니다.
destroy 의 경우는 서블릿 컨테이너의 재량에 따라 서블릿이 더 이상 메모리에 올려둘 필요가 없다고 판단되거나
서블릿 컨테이너가 종료될 때 destroy가 호출됩니다.
Servlet listener
서블릿 컨테이너에서 발생하는 이벤트(라이프사이클, 애트리뷰트, 세션 등)로 특정 코드를 실행해야할 때 사용할 수 있는 개념입니다.
서블릿 컨테이너가 구동 > db 커넥션
각각의 서블릿들에게 서블릿 컨텍스트 리스너를 활용하여 DB 커넥션을 정리하는 일도 수행할 수 있음
Servlet filter
doGet 등의 위치로 가기 전에 전처리를 하고 싶은 경우 사용하는 것입니다.
여러개의 서블릿에 추가 작업 및 특정 url 패턴에도 작업을 추가할 수 있습니다.
filter들은 체인형태로 순차적으로 적용되기 때문에 반드시 다음 체인으로 넘어가도록 코드를 작성해주어야 서블릿 컨테이너에서 서블릿으로 요청이 전달되게 됩니다.
각각의 필터에서는 javax.servlet.Filter 를 구현하여 doFilter 메소드 내에서 doFilter를 호출하여 다음 필터로 넘어가도록 구현해야합니다. 마지막 필터인경우에는 Servlet으로 요청이 넘어 갈 것입니다.
Spring 을 적용한 servlet
1. 스프링 IoC 컨테이너 활용
스프링 IoC컨테이너인 Application Context를 서블릿 어플리케이션 생명주기에 맞춰 바인딩 해줍니다. 웹 어플리케이션에 등록되어 있는 서블릿들이 사용할 수 있도록 Application Context 를 만들어서 그 Application Context 를 Servlet Context 에 등록해줍니다.
서블릿이 종료될 시점에 Application Context 를 제거해줍니다. 이렇게 Servlet Context 의 생명주기에 맞춰서 ApplicationContext를 제공해주는 것입니다.
이를 이용하기 위해선 ApplicationContext 를 만들어줘야합니다.
1) dependency 추가 - spring boot 가 아니므로 버전을 추가해줘야합니다.
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.1.3.RELEASE</version>
</dependency>
2) web.xml에 listener 추가
아래와 같이 설정해주면 Config 파일을 이용해 applicationContext 를 만들게됩니다.
조심해야 할 것은 context-param은 filter보다 먼저 설정해줘야합니다
<context-param>
<param-name>contextClass</param-name>
<param-value>org.springframework.web.context.support.AnnotationconfigWebApplicationContext</param-value>
//ApplicationContext의 타입을 지정해주는 것
<context-param>
<param-name>contextConfiguration</param-name>
<param-value>my.pkg.AppConfig</param-value>
</context-param>
//Java 설정파일을 지정
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
Dispatcher Servlet
FrontController 패턴
모든 요청을 Cotroller 하나가 받습니다. 이 Controller가 요청을 처리한 Handler들에게 분배를 합니다. 이렇게 분배하는 과정을 dispatch라고 합니다.
구조
Dispatcher Servlet은 요청을 한곳에서 받아서 필요한 처리를 수행한 뒤 요청에 맞는 handler 로 dispatch 하고 해당 handler의 실행결과를 HttpResponse 형태로 만드는 역할을 합니다.
Root WebAapplicationContext가 ContextLoaderListener에 의해 등록된 ApplicationContext이며 Servelet WebApplicationContext가 그것을 상속받아 DispatcherServelet에서 자동으로 만든 ApplicationContext입니다.
Root WebApplicationContext - Services, Repositories 등 ContextLoaderListener에 의해 ServletContext에 등록되는 ApplicationContext로 모든 Servlet이 사용가능합니다. web과 관련된 bean들은 존재하지 않습니다.
Servlet WebApplicationContext - Dispatcher Servlet 에서 Root WebApplicationContext를 상속받아 만든 ApplicationContext로 해당 DispatcherServlet안에서만 사용이 가능합니다. Controller, Handler Mapping 등 web과 관련된 bean들이 등록됩니다.
이런 구조를 통해 DispatcherServlet이 공용으로 써야하는 Bean은 Root WebApplicationContext를 통해 사용가능하고 각각의 DispatcherServlet에서 쓰는 bean인 경우에는 Root WebApplicationContext를 통해 사용가능합니다.
설정방법 - web.xml 에 설정
<context-param>
<param-name>contextClass</param-name>
<param-value>org.springframework.web.context.support.AnnotationconfigWebApplicationContext</param-value>
//ApplicationContext의 타입을 지정해주는 것
<context-param>
<param-name>contextConfiguration</param-name>
<param-value>my.pkg.AppConfig</param-value>
</context-param>
//Java 설정파일을 지정
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<servlet>
<servlet-name>app</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServelt</servlet-class>
<init-param>
<param-name>contextClass</param-name>
<param-value>org.springframework.web.context.support.AnnotationConfigWebApplicationContext</param-value>
</init-param>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>me.pkg.Webconfig</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>app</servlet-name>
<url-pattern>/app/*</url-pattern>
</servlet-mapping>
부모는 AppConfig 로 만들어지고 그 하위 dispatcherServlet은 Webconfig를 통해 만들어집니다.
me.pkg.AppConfg
@Configuration
@ComponentScan(excludeFilters=@ComponentScan.Filter(Controller.class))
public class AppConfig{
}
me.pkg.WebConfig
@Configuration
@ComponentScan(userDefaultFilters= false, includesFilters =@ComponentScan.Filter(Controller.class)
public class WebConfig(){
}
이런방식을 통해서 Dispatcher Servlet을 여러개 만들어서 사용할 수 있습니다.
그러나 요즘에는 그런 경우가 거의 드뭅니다. 따라서 하나의 DispatcherServlet 에 등록하여 사용하게 됩니다.
'Java > Spring Framework' 카테고리의 다른 글
Dispatcher Servlet 두번째 (0) | 2021.02.14 |
---|---|
DispatcherServlet (0) | 2021.02.13 |
Null-safety (0) | 2021.02.07 |
AOP (0) | 2021.02.07 |
SpEL (0) | 2021.02.07 |