사내 스터디로 스프링 프레임워크를 직접 자바 코드로 구현하는 것을 주제로 잡아 공부하고 있다.
첫번째는 Servlet이다.
Servlet 이란?
Servlet은 자바를 사용하여 웹 서버에서 실행되는 서버 프로그램입니다.
보통 HTTP 요청을 처리하고, 동적인 웹 콘텐츠를 생성하는데 사용을 합니다.
서블릿은 Java EE(Enterprise Edition) 플랫폼의 일부로,
웹 애플리케이션의 요청과 응답을 처리하기 위한 표준 API를 제공합니다.
Servlet 의 주요 특징
Servlet은 자바 클래스이며, 'javax.servlet' 패키지에 속합니다. HttpServlet 클래스를 상속받아 구현됩니다.
Servlet은 생성, 초기화, 요청 처리, 소멸 의 순서로 라이프사이클을 가집니다.
Servlet 구현 및 테스트
스터디에서는 미션 형식으로 코드를 작성하고 이에 맞는 테스트코드를 작성해서 통과하는 것 까지가 미션의 과정이였습니다.
미션1. /sign-up 경로 요청에 대한 처리 로직을 구현하기
GET
:sign-up.jsp
파일을 렌더링 할 수 있도록 구현한다.POST
:sign-up.jsp
의 입력칸과 버튼을 이용해 회원 가입 기능을 구현한다.
미션1 에서는 /sign-up 경로로 요청이 들어왔을 때, Servlet으로 처리 로직을 구현하는 미션이었습니다.
doGet, doPost
HttpServlet을 상속 받으면 doGet과 doPost메서드를 오버라이딩 해서 사용을 할 수 있습니다.
예를 들어, /sign-up 에 해당하는 Servlet 클래스가 존재 할 때,
doGet 메서드는 /sign-up 주소로 get 요청을 보냈을때 일어나는 일을 처리할 수 있습니다.
그렇다면 doPost는 /sign-up 주소로 post요청이 들어왔을때 일어나는 일을 처리할 수 있을것이라고 생각할 수 있습니다.
풀이
package com.test.mvcframework.boot.web.servlet;
import com.test.mvcframework.boot.web.servlet.user.User;
import com.test.mvcframework.boot.web.servlet.user.UserRepository;
import javax.servlet.RequestDispatcher;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
import static java.lang.System.out;
@WebServlet("/sign-up")
public class SignUpServlet extends HttpServlet {
@Override
public void init() throws ServletException {
out.println("SignUpServlet.init");
super.init();
}
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
out.println("SignUpServlet.doGet");
RequestDispatcher requestDispatcher = req.getRequestDispatcher("sign-up.jsp");
requestDispatcher.forward(req, resp);
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException {
out.println("SignUpServlet.doPost");
out.println(req.toString());
String id = req.getParameter("id");
String pw = req.getParameter("pw");
User user = new User(id,pw);
UserRepository.save(user);
PrintWriter out = res.getWriter();
out.print(id+","+pw);
}
}
@WebServlet("/sign-up") 으로 /sign-up 경로에 요청이 들어오면 SignUpServlet 인스턴스에서 처리해주도록 구현되었습니다.
doGet 메서드가 호출되면 sign-up.jsp 파일을 랜더링 해줍니다.
doPost 메서드가 호출되면 request.body에 포함된 값을 가져와서 새로운 유저를 만들고 저장합니다.
이런식으로 Servlet을 구현해서 http 호출에 대한 처리가 가능합니다.
doGet, doPost 말고도 HttpServlet을 상속받은 클래스가 오버라이딩 해서 사용 가능한 많은 메서드가 존재합니다.
Test Code
@Test
void SIGNUP_SERVLET_RESPONSE() throws IOException, InterruptedException, ClassNotFoundException {
// given
MvcApplicationMain.main(new String[0]);
String url = "http://localhost:8080/sign-up";
HttpClient client = HttpClient.newHttpClient();
// when
HttpRequest request = HttpRequest.newBuilder()
.GET()
.uri(URI.create(url))
.build();
HttpResponse<Void> response = client.send(request, HttpResponse.BodyHandlers.discarding());
// then
Assertions.assertThat(response.statusCode()).isEqualTo(200);
}
위의 테스트코드는 실제로 Servlet이 잘 동작하는지 테스트하는 코드입니다.
main 메서드를 실행시 새로운 url 요청을 만들어서 실제로 호출했을때 정상적으로 작동하는지 테스트 해보았습니다.
https://docs.oracle.com/javaee%2F7%2Fapi%2F%2F/javax/servlet/http/HttpServlet.html
위 공식 문서에서 HttpServlet에 대한 더 자세한 설명이 있습니다.
다음 글에서는 스프링의 DI Container를 구현 해보도록 하겠습니다.
'BackEnd > Java' 카테고리의 다른 글
[Java] 이것이 자바다 - 2장. 변수와 타입 (1) | 2024.06.08 |
---|---|
[Java] 스프링 개구리 책 - 붕어빵틀과 붕어빵에 대한 오해 (0) | 2024.05.27 |
[Spring] 싱글톤 컨테이너, 컴포넌트와 컴포넌트 스캔 (0) | 2024.04.07 |
[Java] Optional(옵셔널) 이란? (0) | 2024.03.21 |
[Java] Thread의 내부 생성자, 메소드 (0) | 2023.12.08 |