코드 그라데이션

프론트 컨트롤러 도입 - v1 본문

Spring/MVC 1

프론트 컨트롤러 도입 - v1

완벽한 장면 2023. 9. 24. 18:30

v1 구조


먼저 컨트롤러를 인터페이스로 만들어놓고, 각 컨트롤러들은 이 인터페이스를 구현한다.

ControllerV1

public interface ControllerV1 {

    void process(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException;
   
}
  • 서블릿과 모양이 똑같은 인터페이스
  • 이것 가지고 구현을 여러 개 할 것이다.
  • 매핑 정보에서 찾아서 호출할 때 다형성을 이용해서 프론트 컨트롤러는 인터페이스에 의존하면서 편리하게 할 수 있음.

로직은 기존 서블릿과 똑같다.

대신에 얘들은 서블릿 상속 대신에 인터페이스를 구현하고, webservlet 같은 게 전혀 없다.

 

 

MemberFormControllerV1 - 회원 등록 컨트롤러

public class MemberFormControllerV1 implements ControllerV1 {

    @Override
    public void process(HttpServletRequest request, HttpServletResponse response) 
    	throws ServletException, IOException {
        
        String viewPath = "/WEB-INF/views/new-form.jsp"; // 뷰 페이지의 경로
        
        RequestDispatcher dispatcher = request.getRequestDispatcher(viewPath);
        // 현재 요청을 지정된 JSP 페이지로 전달할 수 있는 방법을 제공
        
        dispatcher.forward(request, response);
    	// 현재 요청과 응답을 지정된 JSP 페이지로 전달. 
        // 이를 통해 JSP 페이지에서 웹 페이지를 동적으로 생성하고 
        // 응답을 클라이언트로 보낸다.
    }
}
  • 이 컨트롤러 클래스는 웹 애플리케이션의 흐름을 제어하고 원하는 뷰 페이지로 사용자를 리디렉션하는 역할을 수행

 

 

MemberSaveControllerV1 - 회원 저장 컨트롤러

public class MemberSaveControllerV1 implements ControllerV1 {

    private MemberRepository memberRepository = MemberRepository.getInstance();
    // 싱글톤 패턴을 사용하여 리포지토리 인스턴스를 가져옴

    @Override
    public void process(HttpServletRequest request, HttpServletResponse response) 
    	throws ServletException, IOException {
        
        //  HTTP 요청에서 파라미터 읽어오기
        String username = request.getParameter("username");
        int age = Integer.parseInt(request.getParameter("age"));

		// 객체 생성 및 저장 작업
        Member member = new Member(username, age);
        memberRepository.save(member);

        //Model에 데이터를 보관한다.
        //"member"라는 이름으로 member 객체를 HTTP 요청의 속성으로 설정한다. 
        //이렇게 함으로써, 이 데이터는 다음 JSP 페이지에서 사용할 수 있음
        request.setAttribute("member", member);

        String viewPath = "/WEB-INF/views/save-result.jsp";
        RequestDispatcher dispatcher = request.getRequestDispatcher(viewPath); 
        // JSP 뷰 페이지로 현재 요청과 응답을 전달
        
        dispatcher.forward(request, response);
    }
}
  • 이 컨트롤러 클래스는 웹 애플리케이션에서 사용자가 제출한 폼 데이터를 처리하고 결과를 표시하는 역할

 

 

MemberListControllerV1 - 회원 목록 컨트롤러

public class MemberListControllerV1 implements ControllerV1 {

    private MemberRepository memberRepository = MemberRepository.getInstance();

    @Override
    public void process(HttpServletRequest request, HttpServletResponse response) 
    	throws ServletException, IOException {
        
        List<Member> members = memberRepository.findAll();

        request.setAttribute("members", members);
        //"members"라는 이름으로 검색된 멤버 목록을 HTTP 요청의 속성으로 설정. 
        // 이렇게 함으로써, 이 데이터는 다음 JSP 페이지에서 사용할 수 있음.


        String viewPath = "/WEB-INF/views/members.jsp";
        RequestDispatcher dispatcher = request.getRequestDispatcher(viewPath);
        // "members.jsp"라는 JSP 뷰 페이지로 현재 요청과 응답을 전달
        
        dispatcher.forward(request, response);
    }
}

 

 


이제 프론트 컨트롤러

FrontControllerServletV1

@WebServlet(name = "frontControllerServletV1", urlPatterns = "/front-controller/v1/*") 
// 별이 들어가면 하위에 어떤 게 들어와도 무조건 호출된다는 뜻
public class FrontControllerServletV1 extends HttpServlet { //서블릿이어야 한다.

    // 매핑 정보
    private Map<String, ControllerV1> controllerMap = new HashMap<>();

    public FrontControllerServletV1() { // 생성자에 매핑 정보 다 담아버리기
        controllerMap.put("/front-controller/v1/members/new-form", new MemberFormControllerV1());
        controllerMap.put("/front-controller/v1/members/save", new MemberSaveControllerV1());
        controllerMap.put("/front-controller/v1/members", new MemberListControllerV1());
    }

    @Override
    protected void service(HttpServletRequest request, HttpServletResponse response) 
    	throws ServletException, IOException {
        
        System.out.println("FrontControllerServletV1.service");

        String requestURI = request.getRequestURI();
        /*
        이렇게 하면 /front-controller/v1/members/new-form 이러한 형태를 딱 얻어낼 수가 있다.
         */
        ControllerV1 controller = controllerMap.get(requestURI); // 얻은 정보를 꺼내기
        // 인터페이스로 꺼내면 이 코드를 아주 일관성 있게 사용할 수 있게 된다.
        // 호출 된 것은 셋 중에 하나지만, 다형성에 의거하여 부모인 controller로 받을 수 있게 되는 것.

        if (controller == null) { // 예외처리
            response.setStatus(HttpServletResponse.SC_NOT_FOUND); // 404 메시지
            return;
        }

        controller.process(request, response); //인터페이스 바로 호출
    }
}

 

프론트 컨트롤러 분석

urlPatterns

 

controllerMap

 

service()

 

jsp는 이전 MVC에서 사용했던 것을 그대로 사용한다.

- 이미 상대경로로 만들어 놓았기 때문에 쓸 수 있다.

 편의상 만들었지만, 실제 개발할 때에는 절대경로 사용을 권장한다.

 

실행

문제없고

 

3개 등록하고 봐도 잘 등록이 되어있음을 조회 가능하다.

728x90

'Spring > MVC 1' 카테고리의 다른 글

Model 추가 v3  (0) 2023.09.26
View 분리 - v2  (0) 2023.09.25
프론트 컨트롤러 패턴 소개  (0) 2023.09.24
MVC 패턴 - 한계  (0) 2023.09.23
MVC 패턴 - 적용  (0) 2023.09.23
Comments