언어 및 도구들 공부/Spring

PrintWriter 객체 없이 JS 코드를 Java에서 입력

Dr.Mlem 2024. 10. 25. 16:18

Q1.
(08-08 어떻게든 @ResponseBody 와 void 메서드 조합을 고쳐보려는 발악중)
PrintWriter 객체가 없이 JS 코드를 작성해서 동작시킬수는 없어?



A1.
PrintWriter 객체 없이 자바스크립트 코드를 작성하고 동작시키려면, Spring MVC의 ModelAndView를 사용하여 뷰 템플릿에서 자바스크립트를 렌더링할 수 있습니다. 예를 들어, showAlert 메서드를 사용하지 않고, 컨트롤러 메서드에서 직접 자바스크립트를 포함한 뷰를 반환할 수 있습니다.

 


다음은 ModelAndView를 사용하여 자바스크립트를 포함한 뷰를 반환하는 예시입니다:

1. showAlert 메서드를 제거하고, 컨트롤러 메서드에서 직접 자바스크립트를 포함한 뷰를 반환합니다.

@PostMapping("/department/add_ok")
public ModelAndView addOk(HttpServletRequest request,
    @RequestParam("dname") String dname,
    @RequestParam("loc") String loc) {
    
    // 정상적인 경로로 접근한 경우 이전 페이지 주소는
    // 1) http://localhost:8080/department
    // 2) http://localhost:8080/department/detail/학과번호
    // 두 가지 경우가 있다.
    String referer = request.getHeader("referer");

    if (referer == null || !referer.contains("/department")) {
        return new ModelAndView("redirect:/department")
            .addObject("message", "올바르지 않은 접근입니다.");
    }

    // 저장할 값들을 Beans에 담는다.
    Department input = new Department();
    input.setDname(dname);
    input.setLoc(loc);

    try {
        departmentService.addItem(input); // 위에서 만든 input 객체는 참조로 전달 -> 여기서 추가되면서 pk값이 추가됨 -> 원본에도 pk 값이 추가됨.
    } catch (ServiceNoResultException e) { 
        return new ModelAndView("redirect:/department")
            .addObject("message", "서버 오류가 발생했습니다.");
    } catch (Exception e) {
        return new ModelAndView("redirect:/department")
            .addObject("message", "서버 오류가 발생했습니다.");
    }

    // Insert, UPDATE, DELETE 처리를 수행하는 경우에는 리다이렉트로 이동
    // INSERT 결과를 확인할 수 있는 상세 페이지로 이동해야 한다.
    // 상세 페이지에 조회 대상의 PK 값을 전달해야 한다.
    ModelAndView mav = new ModelAndView("redirect:/department/detail/" + input.getDeptno());
    mav.addObject("message", "등록되었습니다.");
    return mav;
}

2. 뷰 템플릿 (예: detail.jsp 또는 detail.html)에서 자바스크립트를 사용하여 메시지를 표시하고 리다이렉트를 처리합니다.
예를 들어, JSP를 사용하는 경우:

이렇게 하면, 컨트롤러에서 ModelAndView를 사용하여 메시지를 전달하고, 뷰 템플릿에서 자바스크립트를 사용하여 메시지를 표시할 수 있습니다. PrintWriter 객체를 사용하지 않고도 자바스크립트를 포함한 응답을 생성할 수 있습니다.

 

 

Q2.

현재 pritnwriter에서 입력하는 위치는 Java 코드 상인거지?

 

 

 

A2.

네, 현재 PrintWriter를 사용하여 자바 코드 내에서 HTML 및 자바스크립트를 작성하고 있습니다. 이 방식은 서버 측에서 클라이언트로 전송될 HTML 응답을 직접 생성하는 것입니다.

 


다음은 현재 showAlert 메서드의 코드입니다:

 

public void showAlert(int statusCode, String message) {
    /** 알림 메시지 표시 후 바로 이전 페이지로 이동 --> helper로 이식 예정 */
    // http 403 forbidden 클라이언트 오류 상태 응답 코드는 서버에 요청이 전달되었지만,
    // 권한 때문에 거절되었다는 것을 의미
    response.setStatus(statusCode);
    response.setContentType("text/html; charset=utf-8");

    PrintWriter out = null;
    try {
        out = response.getWriter();
    } catch (IOException e) {
        log.error("응답 출력 스트림 생성 실패", e);
        return;
    }
    
    if (message != null && !message.equals("")) { // 메시지가 있다면 메시지를 뿌린다
        out.println("<script>");
        out.println("alert('" + message + "');");
        out.println("</script>");       
    }                                         
}

 

이 코드는 자바 코드 내에서 PrintWriter 객체를 사용하여 HTML 및 자바스크립트를 작성하고 있습니다. 이 방식은 간단하지만, 더 나은 방법은 뷰 템플릿을 사용하는 것입니다. 뷰 템플릿을 사용하면 코드의 가독성과 유지보수성이 향상됩니다.

 


다음은 뷰 템플릿을 사용하여 자바스크립트를 포함한 응답을 생성하는 예시입니다:

1. showAlert 메서드를 수정하여 ModelAndView를 반환합니다.

 

public ModelAndView showAlert(int statusCode, String message, String redirectUrl) {
    ModelAndView mav = new ModelAndView("alert");
    mav.addObject("statusCode", statusCode);
    mav.addObject("message", message);
    mav.addObject("redirectUrl", redirectUrl);
    return mav;
}

 

2. 컨트롤러 메서드에서 showAlert 메서드를 호출합니다.

 

@PostMapping("/department/add_ok")
public ModelAndView addOk(HttpServletRequest request,
    @RequestParam("dname") String dname,
    @RequestParam("loc") String loc) {
    
    // 정상적인 경로로 접근한 경우 이전 페이지 주소는
    // 1) http://localhost:8080/department
    // 2) http://localhost:8080/department/detail/학과번호
    // 두 가지 경우가 있다.
    String referer = request.getHeader("referer");

    if (referer == null || !referer.contains("/department")) {
        return webHelper.showAlert(403, "올바르지 않은 접근입니다.", "/department");
    }

    // 저장할 값들을 Beans에 담는다.
    Department input = new Department();
    input.setDname(dname);
    input.setLoc(loc);

    try {
        departmentService.addItem(input); // 위에서 만든 input 객체는 참조로 전달 -> 여기서 추가되면서 pk값이 추가됨 -> 원본에도 pk 값이 추가됨.
    } catch (ServiceNoResultException e) { 
        return webHelper.showAlert(500, "서버 오류가 발생했습니다.", "/department");
    } catch (Exception e) {
        return webHelper.showAlert(500, "서버 오류가 발생했습니다.", "/department");
    }

    // Insert, UPDATE, DELETE 처리를 수행하는 경우에는 리다이렉트로 이동
    // INSERT 결과를 확인할 수 있는 상세 페이지로 이동해야 한다.
    // 상세 페이지에 조회 대상의 PK 값을 전달해야 한다.
    return webHelper.showAlert(200, "등록되었습니다.", "/department/detail/" + input.getDeptno());
}

 

3. 뷰 템플릿 파일 (alert.jsp 또는 alert.html)을 생성하여 자바스크립트를 포함합니다.
예를 들어, JSP를 사용하는 경우:

 

<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<!DOCTYPE html>
<html>
<head>
    <title>Alert</title>
    <script type="text/javascript">
        <c:if test="${not empty message}">
            alert("${message}");
        </c:if>
        <c:if test="${not empty redirectUrl}">
            window.location = "${redirectUrl}";
        </c:if>
    </script>
</head>
<body>
</body>
</html>

 

이렇게 하면, 자바 코드 내에서 직접 HTML 및 자바스크립트를 작성하지 않고, 뷰 템플릿을 사용하여 응답을 생성할 수 있습니다. 이는 코드의 가독성과 유지보수성을 크게 향상시킵니다.