Web Application이란
Client - Server Architecture
Server
- Server는 Client가 요청한 서비스를 제공
Client
- Client는 서비스를 사용하는 사용자 혹은 사용자의 단말기
Server - Client (예)
- 메일 서버
- 파일 서버
- 파일 서버는 중앙에 위치하면 중앙에 저장된 파일은 여러 사용자가 접근할 수 있다. (ex. 구글 드라이브, 두레이 드라이브)
- 웹 서버
Web Application Architecture란
- 애플리케이션 구성 요소, 미들웨어 시스템, 사용자 인터페이스 및 데이터베이스 간의 상호 작용을 표시하는 "골격" 또는 레이아웃을 의미합니다. 이러한 상호 작용을 통해 여러 응용 프로그램이 동시에 함께 작동할 수 있습니다.
- 데이터가 HTTP를 통해 전달하는 방식을 정의하고 클라이언트와 Backend Server(API Server)가 서로 통신할 수 있도록 한다.
- 모든 사용자의 요청에 대한 유효성 검증
- 권한 기반의 접근(인증)
구성요소
- 웹 브라우저
- HTML 문서
- 이미지 파일 (jpg, png, gif..)
- javascript (객체)
- 웹 서버
- 데이터베이스 서버
- mysql
- mariadb
- oracle
- ms-sql
Web Server
웹 서버는 웹 브라우저와 같은 클라이언트로 부터 HTTP 요청을 받아들이고, HTML 문서와 같은 웹페이지를 반환하는 컴퓨터 프로그램
HTTP, HTTPS request -> HTML 문서 등 response
정의
- 웹 서버(Web Server)는 HTTP 또는 HTTPS를 통해 웹 브라우저에서 요청하는 HTML 문서나 오브젝트(이미지 파일 등)를 전송해 주는 서비스 프로그램을 말한다.
- http 프로토콜을 통해
- 웹 브라우저에서 요청 -> 전송해 주는 서비스 프로그램
Dynamic Web Contents (동적 웹 콘텐츠)
- 방문 시간, 위치, 장치 등 사용자에 특정한 요인이나 요청에 따라 변경되는 콘텐츠
- 동적 웹 콘텐츠는 모든 사용자에게 동일하게 표시되지 않을 수 있으며 사용자와의 상호작용에 따라 변경될 수 있다.
동적 웹 콘텐츠는 사용자의 특정한 요인, 요청에 따라 다른 서비스를 제공.
Static Web Contents
- 웹 서버에 미리 저장되어 있는 콘텐츠
- 모든 사용자에게 동일한 내용이 전달
- HTML 파일, 이미지 등
정적 웹 콘텐츠는 미리 저장된 콘텐츠를 전달하여 모든 사용자에게 같은 서비스 제공
CGI(Common Gateway Interface)
- 웹 서버가 외부 프로그램을 실행할 수 있도록 해주는 인터페이스 명세(specification)
- 외부 프로그램 = 동적 웹 콘텐츠 생성하는 역할
- c, c++, java, php, go ...
- 웹 서버와 CGI 프로그램(Application) 간의 규칙
- 환경변수나 표준입출력을 다룰 수 있는 프로그램 언어라면 어떤 언어든지 확장하여 이용 가능
- 실행 속도나 텍스트 처리의 용이함 등의 이유로 perl이나 python, ruby등의 스크립트 언어를 주로 사용
Java CGI 프로그램
- .class 형태로 컴파일된 Java는 컴파일 방식으로 실행 불가능하다. JVM은 Java를 실행할 수는 있지만 웹 서버와 java application Server간의 통신은 할 수 없다.
- 웹 서버와 Java Application 사이에서 서로 통신할 수 있도록 한 JCGI가 있어야 한다.
JCGI
- Java로 작성한 프로그램을 구동하기 위한 CGI 프로그램
cgi argument object에서 파라미터를 받게 설정하고 JCommander를 통해 newBuilder 후 addObject로 cgi argument object를 넣어주고 build와 parse를 통해 파라미터를 삽입해준다.
public class Main {
public static void main(String[] args) {
CgiArgs cgiArgs = new CgiArgs();
JCommander.newBuilder()
.addObject(cgiArgs)
.build()
.parse(args);
System.out.println("content-type:" + cgiArgs.getContentType());
System.out.println("method:" + cgiArgs.getMethod());
System.out.println("query-string:" + cgiArgs.getQueryString());
System.out.println("server-name:" + cgiArgs.getServerName());
System.out.println("server-port:" + cgiArgs.getPort());
System.out.println("path:" + cgiArgs.getPath());
System.out.println("body:" + cgiArgs.getBody());
}
}
Java CGI 문제점
- 별도의 스크립트가 필요
- jcgi
- Java 런타임 인터프리터 실행
- main class 지정
- 환경변수를 명시적으로 Java 프로그램에 넘겨줘야 함
- java -jar /some/path/javacgi.jar
- java -jar -D cgi.request_method=$REQUEST_METHOD /som/path/javacgi.jar
Fast CGI
FastCGI의 주 목적은 웹 서버와 CGI 프로그램 통신 시 발생하는 부하를 줄임으로써 서버가 한 번에 더 많은 웹 페이지 요청을 관리할 수 있게 하는 것이다.
- 하나의 큰 프로세스로 동작한다.
- 대부분의 웹 서버가 FastCGI를 제공한다.
Java는 Web Application Server인 Tomcat을 사용한다.
- Web Application Server == WAS 라고 표현한다.
Servlet이란
정의
- Java를 사용하여 동적 웹 콘텐츠를 생성하는 서버 측 프로그램
- 쉽게 말해, Java로 만든 CGI 프로그램 같은 것
- Servlet 인터페이스를 정의
- 즉 Servlet 인터페이스를 구현 -> java로 구현한 CGI 프로그램이라 할 수 있다.
CGI의 단점을 해결한?
- 요청마다 새로운 프로세스가 생성 (CGI) -> 멀티 스레드로 해결
- 스레드는 누가 생성하고 관리하나 -> 컨테이너의 등장
Servlet Architecture

Servlet Container (wiki)
- 웹 컨테이너(Web Container, 또는 서블릿 컨테이너)는 웹 서버의 컴포넌트 중 하나로 자바 서블릿과 상호작용한다.
- 웹 컨테이너는 서블릿의 생명주기를 관리하고, URL과 특정 서블릿을 맵핑 하며 URL 요청이 올바른 접근 권한을 갖도록 보장한다.
- 웹 컨테이너는 서블릿, Java Server Page(JSP) 파일, 그리고 서버-사이드 코드가 포함된 다른 타입의 파일들에 대한 요청을 다룬다.
- 웹 컨테이너는 서블릿 객체를 생성하고, 서블릿을 로드와 언 로드하며, 요청과 응답 객체를 생성하고 관리하고, 다른 서블릿 관리 작업을 수행한다.
- 웹 컨테이너는 웹 컴포넌트 Java EE 아키텍처 제약을 구현하고, 보안 병행성(concurrency), 생명주기 관리, 트랜잭션, 배포 등 다른 서비스를 포함하는 웹 컴포넌트의 실행 환경을 명세한다(specify)
Java EE
- Java 언어 플랫폼 중의 하나
- 대용량, 멀티 티어의 엔터프라이즈 애플리케이션을 실행하고 운영할 수 있는 기술과 환경을 제공
- 특정 운영체제와 미들웨어에 종속되지 않고 정보 교환 및 애플리케이션 호환이 가능한 플랫폼을 제공하는 것이 목적
Java 언어 플랫폼
- Java 언어로 작성된 프로그램이 실행되는 특정한 환경
- JDK 1.2 부터 시작
Java 언어 플랫폼의 종류
Java SE (Standard Edition)
- Java 2 Platform, Standard Edition 줄여서 J2SE 라고 불렸음
- 일반적인 응용 프로그램 개발 용도
Java EE (Enterprise Edition)
- Java 2 Platform, Enterprise Edition 줄여서 J2EE라고 불렸음
-Java SE를 확장하여 분산 컴퓨팅, 웹서비스와 같은 엔터프라이즈 환경을 지원
Java ME (Micro Edition)
- Java 2 Platform, Micro Edition 줄여서 J2ME라고 불렸음
- 임베디드 시스템이나 모바일 디바이스를 위한 개발 환경을 지원
JavaFx
- 데스크톱 애플리케이션 및 리치 웹 애플리케이션 개발 환경을 지원
Jarkarta EE
- 오라클이 2017년 Java EE 8 릴리즈를 마지막으로 오픈소스 SW를 지원하는 비영리 단체인 Eclipse 재단에 Java EE 프로젝트를 이관
WAS
WAS(Web Application Server)
- 영미권에서는 주로 (Java) Application Server 라고 부름
- 주로 정적 웹 콘텐츠를 처리하는 웹 서버(apache httpd, nginx)와 구분하기 위한 용도
- Servlet Container(=Web Container), EJB Container 등의 역할을 수행하며
- 동적 웹 콘텐츠를 생성하기 위한 웹 애플리케이션과 서버 환경을 만들어 동작시키는 기능을 제공
tomcat
- apache 재단에서 개발한 무료 오픈소스 WAS
- Servlet Container의 reference 구현
Servlet은 API다
Servlet API
- Java EE에서는 Servlet API Spec만 정의
- 실제 구현은 WAS에서 담당
정리
Servlet
- Java를 사용하여 동적 웹 콘텐츠를 생성하는 서버 측 프로그램
- CGI 단점 해결 -> Servlet Container 도입
CGI는 각 요청마다 프로세스를 생성하야 해서 무겁고 느린 단점이 있었는데 이것을 멀티 스레드 방식으로 Servlet을 관리하도록 Servlet Container를 도입하여 단점을 해결하였다.
Servlet Container
- Servlet의 생명주기를 관리하고, URL과 특정 서블릿을 맵핑하며 URL 요청 처리
- Java EE 아키텍처에 속함
Java EE
- Java 언어로 엔터프라이즈 애플리케이션을 개발하고 운영할 수 있도록 지원해 주는 플랫폼
- 현재는 Eclipse 재단으로 운영이 넘어가서 JarKarta EE로 변경됨
WAS
- Web Application Server
- =Servlet Container
tomcat
- apache 재단에서 만든 WAS 중의 하나
- Servlet Container의 reference 구현
- 사실상, Servlet Container = WAS = tomcat
웹 서버와 WAS 연동 - Reverse Proxy
Proxy
- 자원을 요청하는 클라이언트와 자원을 제공하는 서버 사이에서 중재자 역할을 하는 서버 프로그램
Forward Proxy
- 사용자의 요청을 실제 서버가 직접 받는 것이 아니라 중간에서 포워드 프록시 서버가 대신 요청받아 실제 서버에 연결하여 그 결과를 클라이언트에 전달(forward)
- Cashing을 통한 성능 향상
- 웹 사용 환경 제한을 통한 보안 강화
요청을 캐싱해 두고 이전과 동일한 요청에 대해 서버에 요청을 날리지 않고, 이미 가지고 있는 캐싱 데이터로 빠르게 클라이언트에게 응답을 해 줄 수 있다.
특정 웹사이트에 접속하려고 하면 접속이 제한되는 경우가 종종 있는데 이 것은 포워드 프록시 서버를 두어서 내부망의 컨텐츠 액세스 규칙을 정의해두었기 때문이다.
프록시 서버를 이용하면 실제 IP 주소를 숨길 수 있으며 웹사이트에서는 원래 IP 주소가 아닌 프록시 서버의 주소를 인식하게 된다.
Reverse Proxy
- 보안상의 이유로 DMZ 존에 웹 서버를 두고 Reverse Proxy로 설정하고 WAS는 내부망에 위치시킴
- 상황에 맞게 웹서버나 WAS를 유연하게 늘릴 수 있음
서버가 여러개일 때 한 서버에만 트래픽이 몰리는 것을 리버스 프록시가 여유로운 서버로 요청을 해서 서버 밸런싱을 맞춰주기 위해 사용 이 것을 로드 밸런싱이라고 한다.
클라이언트의 모든 요청은 리버스 프록시 서버 주소로 요청이 되기 때문에, 본 서버의 주소를 숨길 수 있다.
캐싱의 장점은 포워드 프록시와 동일하다.
클라이언트 측에게 데이터(response)를 보내주는 것이 포워드 프록시라면, 백엔드 측에게 요청 데이터(Request)를 보내주는 것이 리버스 프록시라고 정의할 수 있다.
servlet-api 의존 라이브러리 scope가 provided인 이유
- provided는 compile 시점에 필요하고 runtime 시점에는 container가 제공하기 때문에 servlet-api scope가 provided이다.
Servlet 실습 정리
Servlet load-on-startup
서블릿은 브라우저에서 최초 요청 시 init() 메서드를 실행한 후 메모리에 로드되어 기능을 수행한다.
따라서 최초 요청에 대해서 실행시간이 길어질 수 있다는 단점이 있다.
이런 단점을 보안하기 위해 생긴 기능이 load-on-startup 기능이다.
load-on-startup 특징
- 톰캣 컨테이너가 실행되면서 미리 서블릿을 실행
- 지정한 숫자가 0보다 크면 톰켓 컨테이너가 실행되면서 서블릿이 초기화된다.
- 지정한 숫자는 우선순위를 의미하며, 작은 숫자부터 먼저 초기화 된다.
Servlet 초기값 설정
- webapp 내부에서 servlet을 설정할 때 init-param을 통해 이름과 값을 설정할 수 있다.
- servlet 내부에서 값을 가져오기 위해서는 init메소드를 오버라이딩 하여 파라미터로 받아오는 ServletConfig 내부에 있는 getInitaParameter(이름)을 사용하여 가져올 수 있으며 서블릿 로직을 수행하는 함수에서는 getServletCongif()를 통해 ServletConfig 객체를 가져와서 위와 같이 수행하면 초기 값을 가져올 수 있다.
ServletContext
Context란
- 사전적 의미: 문맥, 상황, 배경
- 소프트웨어 개발에서는 Execution Context의 의미로 많이 사용
- 실행 환경 그 자체 (runtime)
- 설정 정보 (Configuration)
소프트웨어 개발에서는 실행 환경이나 설정 정보로 많이 사용된다.
ServletContext란
- Servlet Container 실행 환경
- Servlet과 Servlet Container 간에 연동을 위해 사용
- 웹 애플리케이션에 포함된 Servlet 들은 동일한 ServletContext를 공유
- Servlet끼리 자원을 공유하는 데 활용
- Servlet Container 실행 시 생성되고 Servlet Container 종료 시 소멸
Servlet Context 기능
- 환경 정보 제공 (context path, servlet version, real path 등)
- 설정 정보 제공 (init param, attribute 등)
- Servlet / Filter / Listener 등록
- Servlet에서의 파일 접근
web.xml
- 웹 애플리케이션의 배치 정보를 담고 있는 XML 파일
- /WEB-INF/ 디렉터리 하위에 위치
- <web-app> 이라는 하나의 태그 하위로 설정을 기술
web.xml은 Java 웹 애플리케이션에서 사용되는 배치 서술자(descriptor) 파일 중 하나이다.
이 파일은 웹 애플리케이션의 구성과 설정 정보를 정의하는 데 사용된다.
- 웹 애플리케이션의 구성 요소: 서블릿, 필터, 리스너 등과 같은 구성 요소를 정의할 수 있다.
- 서블릿 매핑: 웹 애플리케이션에서 URL과 서블릿 클래스 사이의 매핑을 정의할 수 있다.
- 필터 설정: HTTP 요청 및 응답을 변경하거나 필터링하는 데 사용되는 필터를 정의할 수 있다.
- 보안 설정: 웹 애플리케이션에 대한 보안 설정을 정의할 수 있다.
- 초기화 매개변수: 웹 애플리케이션에 대한 초기화 매개변수를 정의할 수 있다.
WAR(Web Application Archive)
Maven은 Java 프로젝트를 관리하기 위한 빌드 도구이다. Maven은 프로젝트의 라이프 사이클을 정의하고, 프로젝트 빌드와 관련된 여러 작업을 자동화한다. Maven에서 WAR(Web Archive) 빌드는 웹 애플리케이션을 패키징하고 배포할 때 사용된다. WAR 파일은 웹 애플리케이션의 모든 컴포넌트, 설정 파일, 라이브러리 등을 포함하는 파일이다.
Maven에서 WAR 빌드를 위해서는 pom.xml 파일에 WAR 플러그인을 추가해야 한다. WAR 플러그인은 웹 애플리케이션을 빌드하기 위해 필요한 모든 설정을 젝공한다.
WAR 빌드를 수행하려면, Maven 명령어 mvn package를 실행하면 된다. 이 명령어는 Maven의 빌드 라이프 사이클 중 "package" 단계를 실행하며, 이 단계에서 WAR 파일을 생성한다.
WAR 파일은 기본적으로 target 디렉터리 아래에 생성된다. 이 파일은 웹 애플리케이션을 배포하기 위해 웹 서버에 복사할 수 있다. 웹 서버는 WAR 파일을 읽어 웹 애플리케이션을 배치하고 실행한다.
웹 애플리케이션 패키지 디렉터리 구조
- /WEB-INF/ 디렉터리 하위는 외부 요청에서 직접 참조 불가
- /WEB-INF/classes class 파일들 위치
- /WEB-INF/lib 라이브러리 파일들 위치
- web.xml: 배치 기술자 파일
maven-war-plugin
- pom.xml의 dependency에 선언된 각종 라이브러리, java class 파일, resources를 모아서 하나의 Web Application Archive 형태의 압축 파일을 생성한다.
Cookie
사용자가 웹사이트를 방문할 때 해당 웹사이트의 웹 서버에 의해 생성되어 사용자의 브라우저에 저장되는 작은 데이터 블록
- 쿠키는 클라이언트(브라우저) 로컬에 저장되는 키와 값이 들어있는 작은 데이터 파일이다.
- 사용자 인증이 유효한 시간을 명시할 수 있으며, 유효 시간이 정해지면 종료되도 인증이 유지된다는 특징이 있다.
- 쿠키는 클라이언트의 상태 정보를 로컬에 저장했다가 참조한다.
- 클라이언트에 300개깢 쿠키 저장 가능, 하나의 도메인당 20개의 값만 가질 수 있음, 하나의 쿠키값은 4KB까지 저장한다.
- 쿠키는 사용자가 따로 요청하지 않아도 브라우저가 Request시에 Request Header를 넣어서 자동으로 서버에 전송한다.
Cookie 사용 예시
- 방문 사이트에서 로그인 시, "아이디와 비밀번호를 저장하시겠습니까?"
- 팝업창을 통해 "오늘 이 창을 다시 보지 않기" 체크
Optional vs Optional.ofNulluble 차이
- Optional.of는 전달되는 인자값이 Null이 아닌경우에 사용
- Null인경우 NullPointException이 발생함
- Optional.Nullable은 전달되는 인자값이 Null일 가능성이 있을 때 사용
map vs flatMap 차이
- map은 각각 단일 Stream으로 반환
- flatMap은 하나의 Stream으로 반환
cookie 특징
- Browser 내부에 key/value 형태로 데이터를 저장할 수 있다.
- Cookie는 만료 기간을 설정할 수 있으며 서버로 전송됨
- LocalStorage는 브라우저 내부에서만 유지되며 서버로 전송되지 않음
Web Storage와 cookie의 차이점
- 쿠키는 매번 서버로 전송된다.
- 단순 문자열(스크립트)를 넘어 객체정보를 저장할 수 있다.
- 용량의 제한이 없다.
- 영구 데이터 저장이 가능하다.
Web Storage
LocalStorage
저장한 데이터를 명시적으로 지우지 않는 이상 영구적으로 보관이 가능하다. 앞서 말한대로 도메인마다 별도로 로컬 스토리지가 생성된다. Windows 전역 객체의 LocalStorage라는 컬렉션을 통해 저장과 조회가 이루어진다.
SessionStorage
SessionStorage는 데이터의 지속성과 액세스 범위에 특수한 제한이 존재한다. SessionStorage는 windows 전역 객체의 sessionStorage라는 컬렉션을 통해 저장과 조회가 이루어진다.
Session
상태가 없는(stateless) http 프로토콜 상에서 일정 시간동안 같은 사용자로부터의 여러 요청을 하나의 상태로 유지시키는 기술
- 세션은 쿠키를 기반하고 있지만, 사용자 정보 파일을 브라우저에 저장하는 쿠키와 달리 세션은 서버 측에서 관리한다.
- 서버에서는 클라이언트를 구분하기 위해 세션 ID를 부여하며 웹 브라우저가 서버에 접속해서 브라우저를 종료할 때까지 인증상태를 유지한다.
- 물론 접속 시간에 제한을 두어 일정 시간 응답이 없다면 정보가 유지되지 않게 설정이 가능하다.
- 사용자에 대한 정보를 서버에 두기 때문에 쿠키보다 보안에 좋지만, 사용자가 많아질수록 서버 메모리를 많이 차지하게 된다.
- 즉 동접자 수가 많은 웹사이트인 경우 서버에 과부하를 주게 되므로 성능 저하의 요인이 된다.
- 클라이언트가 Request를 보내면, 해당 서버의 엔진이 클라이언트에게 유일한 ID를 부여하는 데 이것이 세션 ID이다.
Session 사용 예시
- 화면을 이동해도 로그인이 풀리지 않고 로그아웃하기 전까지 유지
HTTP의 특징과 쿠키와 세션을 사용하는 이유
HTTP프로토콜의 특성이자 약점을 보완하기 위해서 쿠키 또는 세션을 사용한다.
기본적으로 HTTP 프로토콜 환경은 connectionless, stateless한 특성을 가지고 있기 때문에 서버는 클라이언트가 누구인지 매번 확인해야 한다. 이 특성을 보완하기 위해 쿠키와 세션을 사용하게 된다.
connectionless
클라이언트가 요청을 한 후 응답을 받으면 그 연결을 끊어버리는 특징
HTTP는 먼저 클라이언트가 request를 서버에 보내면, 서버는 클라이언트에게 요청에 맞는 response를 보내고 접속을 끊는 특성이 있다.
헤더에 keep-alive라는 값을 줘서 커넥션을 재활용하는데 HTTP1.1에서는 이것이 디폴트다.
HTTP가 tcp위에서 구현되었기 때문에 (tcp는 연결지향, udp는 비연결지향) 네트워크 관점에서 keep-alive는 옵션으로 connectionless의 연결비용을 줄이는 것을 장점으로 비연결지향이라 한다.
stateless
통신이 끝나면 상태를 유지하지 않는 특징
연결을 끊는 순간 클라이언트와 서버의 통신이 끝나며 상태 정보는 유지하지 않는 특성이 있다.
쿠키와 세션은 위의 두 가지 특징을 해결하기 위해 사용한다.
예를 들어, 쿠키와 세션을 사용하지 않으면 쇼핑몰에서 옷을 구매하려고 로그인을 했음에도, 페이지를 이동할 때마다 계속 로그인을 해야 한다.
쿠키와 세션을 사용했을 경우, 한번 로그인을 하면 어떠한 방식에 의해서 그 사용자에 대한 인증을 유지하게 된다.