> Hello World !!!

     

@syaku

#4 스프링 XML , 스프링 유효성검사 - 스프링 프레임워크 게시판 : Spring Framework Hibernate Validator XML Marshaller

written by Seok Kyun. Choi. 최석균


스프링 프레임워크 연재 포스팅

2014/07/21 - [개발노트/Spring] - 스프링 프레임워크 게시판 #1 STS 설치 및 스프링 프로젝트 만들기 : Spring Framework Hello, World!!!
2014/07/21 - [개발노트/Spring] - 스프링 프레임워크 게시판 #2 스프링 프로젝트 만들기 : Spring Framework Create Project
2014/07/21 - [개발노트/Spring] - 스프링 프레임워크 게시판 #3 스프링 MyBatis 설정하기 및 로그출력 : Spring Framework MyBatis Log4jdbc
2014/07/21 - [개발노트/Spring] - 스프링 프레임워크 게시판 #4 스프링 XML , 스프링 유효성검사 : Spring Framework Hibernate Validator XML Marshaller
2014/07/21 - [개발노트/Spring] - 스프링 프레임워크 게시판 #5 스프링 트랜잭션 : Spring Framework Transaction
2014/07/21 - [개발노트/Spring] - 스프링 프레임워크 게시판 #6 스프링 파일업로드 : Spring Framework FileUpload
2014/07/28 - [개발노트/Spring] - 스프링 프레임워크 게시판 #부록 스프링 검색 및 조회수 올리기 , 스프링 한글깨짐: Spring Framework Cookie


개발 환경

Mac OS X 10.9.4
JAVA 1.6
Apache Tomcat 7.x
MySQL 5.x
Spring 3.1.1
Spring Tool Suite 3.5.1
Maven 2.5.1
myBatis 3.2.7
jQuery 1.11.0

2014.07.19 Written by 최석균 (Syaku)

 

소스파일 : source-4.zip


4. 게시판 유효성검사

프론트앤드를 개발할때 모든 문제점을 실시간으로 검사 및 갱신할 수 있는 파이어버그를 사용하는 것이 좋다. 파이어버그는 파이어폭스의 플러그인으로 설치되므로 파이어폭스를 설치해야 한다. 파이어버그는 웹표준부터 자바스크립트 오류 등 각종 정보를 제공하는 막강한 디버깅용 툴이다. 크롬이 좋다면 크롬용 개발자툴을 사용해도 된다.

등록 뷰페이지에 입력 항목 유효성검사하기

유효성검사란 입력 항목에 값을 정해진 표준으로 정확히 입력하였는 지 검사하는 것을 말한다.
뷰페이지의 유효성검사는 jQuery 를 이용하여 개발한다.

bbs.write.jsp 파일을 열어 jQuery 를 사용하기 위해 스크립트를 head 사이에 추가한다.

<script src="http://code.jquery.com/jquery-1.11.0.min.js"></script>
<script src="http://code.jquery.com/jquery-migrate-1.2.1.min.js"></script>

게시글을 작성할때 필수적으로 입력해야할 항목을 jQuery 로 필터하는 작업이다.

@소스 bbs.write.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>

<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<!DOCTYPE html>
<html lang="ko">
  <head>
    <meta charset="utf-8">
    <title>스프링프레임워크 게시판</title>

    <script src="http://code.jquery.com/jquery-1.11.0.min.js"></script>
    <script src="http://code.jquery.com/jquery-migrate-1.2.1.min.js"></script>
  </head>
  <body>

    <script>

    // 페이지 로딩이 완료되고, jQuery 스크립트가 실행된다.
    jQuery(function (){

        // 저장 버튼을 클릭할때 이벤트 발생
        jQuery('#save').click(function() {
            var subject = jQuery('#form #subject').val();
            if (subject == '') {
                alert('제목을 입력하세요.');
                return;
            }

                jQuery('#save').submit();
        });
    });

    </script>

    <form id="form" method="post" action="./write_ok">
    <input type="hidden" name="idx" id="idx" value="${object.idx}" />
    <div>
    <span>제목</span>
    <input type="text" id="subject" name="subject" value="${object.subject}" />
    </div>
    <div>
    <span>작성자</span>
    <input type="text" id="user_name" name="user_name" value="${object.user_name}" />
    </div>
    <div>
    <span>내용</span>
    <textarea id="content" name="content" rows="10" cols="20">${object.content}</textarea>
    </div>


    <div>
    <button id="save" type="button">저장</button>
    <a href="./">목록</a>
    </div>
    </form>
  </body>
</html>

클릭 이벤트를 사용하여 입력값을 체크하는 스크립트이다. # 은 id 를 말하며 #save 는 id=save 와 같다. 그래서 #save 를 클릭할 경우 위 스크립트가 실행된다.

이번에는 2개 이상의 항목을 필터하는 스크립트를 만들어 본다.

<script>
    // 전송을 위한 체크 함수
    function form_save(form) {
        var is = filter([
        { target : '#subject' , filter : 'empty' , title : '제목' },
        { target : '#content' , filter : 'empty' , title : '내용' } , 
        { target : '#user_name' , filter : 'number' , title : '작성자' }
        ]);

        if (is == true) jQuery(form).submit();
    }

    // 입력 항목의 체크 함수
    function filter(options) {
        var is = true;

        jQuery(options).each(function() {
            var item = this;

            switch (item.filter) {
                case 'empty' :
                    var val = jQuery(item.target).val();
                    if (val == '') {
                        alert(item.title + '을(를) 입력하세요.');
                        jQuery(item.target).focus();
                        is = false;
                    }
                break;

                case 'number' :
                    var val = jQuery(item.target).val();
                    var num_regx = /[^0-9]/;
                    if (num_regx.test(val)) {
                    alert(item.title + '을(를) 숫자만 입력하세요.');
                    jQuery(item.target).focus();
                        is = false;
                    }
                break;

            }
        });
        return is;
    }

</script>

form_save 함수를 호출할때 상수 값은 폼 대상을 넘겨줘야 한다.
그래서 아래와 같이 저장 버튼에 click 이벤트를 정의하고 유효성검사할 대상 폼을 넘겨주었다.

<button id="save" type="button" onclick="form_save('#form');">저장</button>

form_save 함수를 호출하면 filter 함수가 호출되며 함수의 상수값은 json 형식으로 넘겨줘야 한다.
[ { 유효성검사대상 : '' , 유효성검사형식 : '', 유효성검사이름 : ''} ]

한개 이상의 유효성검사를 하기위해 배열을 사용하였다.

filter 함수의 확장성을 위해 switch 문을 이용하여 어떤 필터를 할 것인가를 판단하여 필터를 진행한다. 예제를 위해 user_name 을 숫자만 입력하도록 필터하였다.

숫자 값을 체크하기 위해 정규식을 사용하고 [^0–9] 0에서 9 사이에 값이 아닌 경우를 의미한다.

유효성검사가 잘되는 지 뷰페이지에서 확인한다.

jQuery Ajax 를 이용한 스프링 xml 결과 받기

Ajax 비동기화를 이용하여 요청하고 스프링에서 마샬러를 이용하여 XML 타입으로 응답하고 결과를 jQuery 로 출력하는 작업을 한다. 설명을 위한 예제로 게시판 목록(bbs.list.jsp) 을 사용하여 설명한다.

게시글 목록에 삭제 버튼을 만들어 버튼을 클릭하면 글이 삭제되고 페이지가 새로고침되는 시나리오로 소스를 업데이트 한다.

@소스 bbs.list.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8">
    <title>스프링프레임워크 게시판</title>
    <script src="http://code.jquery.com/jquery-1.11.0.min.js"></script>
    <script src="http://code.jquery.com/jquery-migrate-1.2.1.min.js"></script>

    <script>
    function del(idx) {
        jQuery.ajax({
            type : 'POST' ,
            url : './delete' ,
            data : 'idx=' + idx
        }).done(function(data) {
            console.log(data);
        });

    }
    </script>
  </head>
  <body>
  <h1>${message}</h1>
  <table border="1">
    <colgroup>
    <col width="60"><col><col width="115"><col width="85">
    </colgroup>
    <thead>
    <tr>
        <th scope="col">기능</th>
        <th scope="col">제목</th>
        <th scope="col">작성자</th>
        <th scope="col">등록일</th>
    </tr>
    </thead>

    <tbody>
    <!-- 목록이 반복될 영역 -->
    <c:forEach var="item" items="${list}" varStatus="status">
    <tr>
        <td><button type="button" onclick="del(${item.idx});">${item.idx} 삭제</button></td>
        <td><a href="./${item.idx}">${item.subject}</a></td>
        <td>${item.user_name}</td>
        <td>${item.reg_datetime}</td>
    </tr>
    </c:forEach>

    </tbody>

  </table>
  <div><a href="./write">쓰기</a></div>
  </body>
</html>

del 자바스크립트 함수를 추가하였고, 목록에 삭제버튼을 추가하였다. 글 번호로 데이터를 삭제하기 때문에 del 함수에 글 번호를 넘겨준다.

jQuery.ajax 에는 아래와 같은 속성이 있다.

  • type : 전송 방식 ( GET , POST )
  • url : 전송될 경로
  • data : 전송할때 넘겨줄 파라메터 데이터를 입력한다. 다양한 타입으로 입력할 수 있지만, 기본적인 string 타입으로 입력하였다.

    만약에 쓰기(bbs.write.jsp) 폼에서 입력한 값을 모두 가져올때는 $( form ).serialize(); 사용하면 된다.

ajax 전송이 끝나면 done 객체가 실행된다. jQuery 1.5 이상부터 지원하는 객체이며, 이전 버전 방식을 사용해도 무방하다. done 객체의 상수 data 에 응답 결과가 저장된다.

자바스크립트에서 로그를 출력할때는 console.log(" … "); 를 사용한다. 단 IE에서는 지원하지 않는 다. 오류를 막기 위해 try catch 로 감싸주면 된다.

이제 요청 작업을 했다면 응답 작업을 해줘야 한다. 하지만 ViewController 의 delete 메서드는 결과 값을 넘겨주는 XML이나 JSON 이 아닌 목록으로 리다이렉트되는 구현되었다.
이부분을 XML 데이터로 넘겨주는 작업을 하고 jQuery done 에서 받아 처리하는 작업을 해보도록 한다.

스프링은 XML 뷰를 사용하기 위해 마샬러를 사용한다.

참고 자료 : http://blog.outsider.ne.kr/891

마샬러를 사용하기 위한 라이브러리를 추가한다.
maven 설정 파일 pom.xml 을 열어 마샬러에 필요한한 spring oxm과 XStream 라이브러리를 추가한다.

<!-- spring oxm -->
<dependency>
    <groupId>org.springframework</groupId>
    <artifactId>spring-oxm</artifactId>
    <version>3.1.1.RELEASE</version>
</dependency>

<!-- xstream core -->
<dependency>
    <groupId>com.thoughtworks.xstream</groupId>
    <artifactId>xstream</artifactId>
    <version>1.4.7</version>
</dependency>

스프링 설정 파일 appServlet/servlet-context.xml 을 열어 xml 뷰 출력을 위한 빈를 추가한다. (본 작업이 스프링의 핵심인 AOP라고 한다.)

<!-- XStream -->
<beans:bean id="xstreamMarshaller" class="org.springframework.oxm.xstream.XStreamMarshaller">
<beans:property name="autodetectAnnotations" value="true" />
</beans:bean>

<!-- xmlView -->
<beans:bean id="xmlView" name="xmlView" class="org.springframework.web.servlet.view.xml.MarshallingView">
<beans:property name="marshaller" ref="xstreamMarshaller" />
<beans:property name="contentType" value="application/xml;charset=UTF-8" />
<beans:property name="modelKey" value="xmlData" />
</beans:bean>

2개의 빈 id 를 추가하였다. xmlView 에 마샬러을 주입하고 컨트롤러에서 xmlView 를 호출하면 된다.
이제 컨트롤러의 delete 메서드를 리다이렉트가 아닌 xml 출력으로 수정한다.

@소스 ViewController.java

@Resource(name = "xmlView")
private View xmlView;

@RequestMapping(value = "/delete", method = RequestMethod.POST)
public View procBbsDelete(@RequestParam(value = "idx", required = true) int idx, Model model) {
    this.bbsDao.delete(idx);

    XmlResult xml = new XmlResult();
    xml.setMessage("삭제되었습니다.");
    xml.setError(false);

    model.addAttribute("xmlData", xml);
    return xmlView;
}

// 맨하단에 XmlResult 클래스 추가
// 아래 [영역 1-1] 보다 단순하게 작업하려면 어노테이션을 이용하면 된다. @XStreamAlias("result") 상단에 추가하면 [영역 1-2] 와 같은 결과를 얻을 수 있으며 [영역 1-1] 작업은 생략해도 된다.
class XmlResult {

    private String message;
    private boolean error = false;

    public void setMessage(String message) {
        this.message = message;
    }
    public String getMessage() {
        return this.message;
    }

    public void setError(boolean error) {
        this.error = error;
    }
    public boolean getError() {
        return this.error;
    }
}

등록된 게시물을 삭제하여 XML 결과를 확인한다.

브라우저를 이용한 디버깅방법 파이어폭스를 이용할 경우 F12 키를 누르던가 오른쪽 상단에 벌래모양 아이콘을 클릭한다.


<com.syaku.bbs.XmlResult>
<message>삭제되었습니다.</message>
<error>false</error>
</com.syaku.bbs.XmlResult>

사용하기에 불편해보인다. 그래서 XML 구조를 변경하기 위해 아래의 작업을 추가한다. [영역 1-1]

@Resource(name = "xstreamMarshaller")
private XStreamMarshaller xstreamMarshaller;

XStream xst = xstreamMarshaller.getXStream();
xst.alias("result", XmlResult.class);

procBbsDelete 메서드 이전에 @Resource 어노테이션을 추가하고, procBbsDelete 메서드 안에 XStream 소스를 추가한다.
alias 를 이용하여 xml root 명을 변경할 수 있다. 자세한 설며은 XStream 공식 사이트를 참조한다.

XStream : http://xstream.codehaus.org

다시 게시물 삭제 요청을 하면 다음과 같은 결과를 얻을 수 있다. [영역 1-2]

<result>
<message>삭제되었습니다.</message>
<error>false</error>
</result>

다시 jQuery 로 돌아와서 xml 데이터의 메세지를 출력하고 목록 페이지를 새로고침 해보기로 한다. 아래의 소스로 업데이트한다.

    <script>
    function del(idx) {
        jQuery.ajax({
            type : 'POST' , 
            url : './delete' ,
            data : 'idx=' + idx
        }).done(function(data) {
            var message = jQuery(data).find("message").text();
            var error = jQuery(data).find("error").text();
            alert(message);
            if (error == 'false') location.reload();
        });
    }
    </script>

게시물이 삭제되고 삭제되었습니다. 라는 메세지를 경고창으로 보이게 된다. 그리고 error 가 false 인 경우 페이지를 리로드하게 하면 된다.

Hibernate Validator 을 이용한 스프링 유효성검사 그리고 메세지 국제화

이전 작업은 웹페이지에서 jQuery로 유효성 검사를 했다면, 이번에는 확실한 검사를 위해 스프링 컨트롤러에서 유효성검사를 하고 오류를 출력해보도록 한다.
유효성검사를 위해 컨트롤러를 ajax 방식으로 변경한다.

@소스 ViewController.java

@RequestMapping(value = "/write_ok", method = RequestMethod.POST)
public View procBbsWrite(@ModelAttribute("bbsVo") BbsVo bbsVo,Model model) {
    XStream xst = xstreamMarshaller.getXStream();
    xst.alias("result", XmlResult.class);

    XmlResult xml = new XmlResult();
    Integer idx = bbsVo.getIdx();

    if (idx == null || idx == 0) { 
        this.bbsDao.insert(bbsVo);
        xml.setMessage("추가되었습니다.");
        xml.setError(false);
    } else {
        this.bbsDao.update(bbsVo);
        xml.setMessage("수정되었습니다.");
        xml.setError(false);
    }

    model.addAttribute("xmlData", xml);
    return xmlView;
}

뷰페이지 bbs.write.jsp 를 열어 아래 소스로 수정한다.

@소스 bbs.write.jsp

if (is == true) {
  jQuery.ajax({
      type : 'POST' , 
      url : './write_ok' ,
      data : jQuery('#form :input').serialize()
      }).done(function(data) {
      var message = jQuery(data).find("message").text();
      var error = jQuery(data).find("error").text();
      alert(message);
      if (error == 'false') location.href = './';
      });
  }

자바스크립트 form_save 함수에 if (is == true) jQuery(form).submit(); 부분을 제거하고 위와 같이 수정한다. 그리고 폼태그의 속성을 수정한다. <form id="form”>
jQuery(‘#form :input’).serialize() 코드가 form 태그 안에 있는 모든 input, textarea, select 등 데이터 정보를 수집한다.

게시물을 등록하고 수정하여 정삭적으로 작동하는 지 확인한다.

이제 스프링 컨트롤러에 유효성검사를 적용해보자. 유효성검사를 위해 Hibernate Validation 라이브러리를 Maven 에 추가한다.
pom.xml 열어 아래의 소스를 추가한다.

<!-- Hibernate Validation -->
<dependency>
    <groupId>org.hibernate</groupId>
    <artifactId>hibernate-validator</artifactId>
    <version>5.1.1.Final</version>
</dependency>

그리고 BbsVo.java 소스를 열어 유효성검사 어노테이션을 적용한다.

@NotEmpty(message="제목을 입력하세요.")
private subject;

제목 항목에 빈 값을 허용하지 않게 하였다. 이젠 유효성검사 후 오류에 대한 처리를 위해 컨트롤러도 아래와 같이 수정한다.

public View procBbsWrite(@ModelAttribute("bbsVo") @Valid BbsVo bbsVo, BindingResult result, Model model) { … 생략

procBbsWrite 메서드에 @Vaild 를 추가하고 BindingResult result 를 추가하였다.
bbsVo 를 유효성검사 대상으로 지정하였고, 검사 결과를 result 변수로 받을 수 있다.

이제 오류를 판단하고 오류를 출력해본다.

if (result.hasErrors()) {
    xml.setMessage("오류발생.");
    xml.setError(true);
    model.addAttribute("xmlData", xml);
    return xmlView;
}

hasErrors 객체로 오류여부를 알 수 있으며, return 하여 작업을 종료한다.
테스트를 위해 게시판에 글을 작성하거나 수정해본다. 오류가 발생할 경우 오류발생 메세지의 경고창이 출력된다.

이젠 정해진 메세지가 아니라, 유효성검사에 맞는 메세지를 출력해본다.
BbsVo 에 @NotEmpty(message="제목을 입력하세요.”) message 변수에 메세지를 입력해 놓은 상태이다. 본 메세지를 출력하려면 아래와 같이 코딩하면 된다.

if (result.hasErrors()) {

    String message = null;
    List<FieldError> errors = result.getFieldErrors();
    for (FieldError error : errors ) {
        message = error.getObjectName() + " - " + error.getDefaultMessage();
    }


    xml.setMessage(message);
    xml.setError(true);
    model.addAttribute("xmlData", xml);
    return xmlView;
}

result 객체의 오류 필드를 목록 타입으로 받아 메세지를 추출하면 된다.
더 간단한 소스는 아래와 같다. 필요에 따라 사용하면 된다.

String message = (String) result.getFieldErrors().iterator().next().getDefaultMessage();
xml.setMessage( message );

Hibernate Validation 에서 다양한 유효성검사를 제공하고 있다.

@AssertFalse : false 인 경우 성립
@AssertTrue : true 인 경우 성립
@DecimalMax(value=) : 지정된 값 이하의 실수인 경우 성립
@DecimalMin(value=) : 지정된 값 이상의 실수인 경우 성립
@Future : 대상 날짜가 현재보다 미래인 경우 성립
@Past : 대상 날짜가 현재보다 과거인 경우 성립
@Max(value) : 지정된 값보다 작을 경우 성립
@Min(value) : 지정된 값보다 클 경우 성립
@NotNull : 값이 NULL 이 아닌 경우 성립
@Null : 값이 NULL 인 경우 성립
@Size(min=, max=) : 문자열, 배열이 지정된 값 사이인 경우 성립
@NotEmpty : 빈 값이 아닌 경우 성립

더 많은 정보는 공식 튜토리얼에서 참고한다.

http://docs.jboss.org/hibernate/validator/5.1/reference/en-US/html/chapter-bean-constraints.html

이번에는 메세지를 자바 코드안에 직접 코딩하지 않고 프로퍼티로 따로 관리해보도록 한다.
유효성검사를 위한 완전한 BbsVo 소스는 아래와 같다.

@소스 BbsVo.java

package com.syaku.bbs.dao;

import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;
import org.hibernate.validator.constraints.NotEmpty;

public class BbsVo {
    private Integer idx;

    @NotNull
    private String user_name;

    @Size(max = 250)
    @NotEmpty
    private String subject;

    @NotEmpty
    private String content;
    private String reg_datetime;

    생략 …
}

메세지 프로퍼티를 생성한다. src/main/java/com/syaku/bbs 경로 아래 파일을 생성한다.

@소스 message.properties

NotNull.bbsVo.user_name = 이름을 입력하세요.

Size.bbsVo.subject = 제목을 250자 이하로 입력하세요.
NotEmpty.bbsVo.subject = 제목을 입력하세요.

NotEmpty.bbsVo.content = 내용을 입력하세요.

어노테이션.클래스.메서드 순으로 프로퍼티명으로 만들면 된다. 클래스명은 첫글자를 소문자로 해야한다.

메세지 프로퍼티를 생성할때 주의할점은 properties 는 UTF-8 을 지원하지 않는 다.
그래서 이클립스에서 한글을 작성하면 자동으로 유니코드로 변경되어 내용을 알 수 없게된다.
이 문제점을 해결하기 위해 Properties Editor 플러그인을 설치하면 된다.

이클립스 마켓에서 Properties Editor 검색 후 설치하고 이클립스를 재시작한다.
이미 열려있는 프로퍼티 파일들은 모두 닫고 Properties Editor 로 프로퍼티 파일을 다시 열어야 된다.
이제 한글을 입력하더라도 유니코드로 자동으로 변경되지 않고 내용을 그대로 유지할 수 있다.

이제 스프링에 적용한다. appServlet/servlet-context.xml 열어 messageSource 빈을 추가한다.

<beans:bean id="messageSource" class="org.springframework.context.support.ResourceBundleMessageSource" >
<beans:property name="basenames" value="com/syaku/bbs/message" />
</beans:bean>

그리고 ViewController 에 메세지를 주입한다.

@Resource(name="messageSource")
private MessageSource messageSource;

String message = messageSource.getMessage(result.getFieldError(), Locale.getDefault());

procBbsWrite 메서드에 message 변수를 위 소스로 변경한다.

혹시 메시지 프로퍼티를 찾을 수 없다는 오류 메세지가 발생할 경우가 있다. 이유는 classpath 를 찾을 수없어 오류가 발생하는 문제이다. src/main/resources 폴더에 메세지 프로퍼티를 생성하였다면 classpath 를 찾지 못할 가능성이 높다. 그래서 이클립스 Build Path 를 등록해야 한다. 우선 STS 에서 프로젝트를 선택하고 오른쪽 마우스를 클릭하여 옵션메뉴를 활성화 시킨다.

Build Path > Configure Build Path ..선택한다. 그리고 소스탭에서 프로젝트/src/main/resources 경로에 Included 를 보면 자바만 설정되어 있다.
Add Folder 을 눌러서 **/*.properties 를 등록하고 적용한다. 그리고 프로젝트를 리로드하고 재시작한다. 만약 안될 경우 이클립스를 재시작해본다.

모든 작업을 마쳤다면 게시글을 등록하거나 수정하여 메세지가 출력되는 지 테스트한다.

메세지 국제화

국제화란 다양한 나라의 언어를 지원하는 것을 말하며, 국제화 테스트를 위해 영문 메세지를 추가하였다.

src/main/java/com/syaku/bbs 경로 아래 영문 메세지 프로퍼티를 생성한다.

@소스 message_en.properties

NotNull.bbsVo.user_name = 이건 영문이다. 레드선~ 이름을 입력하세요.

Size.bbsVo.subject = 이건 영문이다. 레드선~ 제목을 250자 이하로 입력하세요.
NotEmpty.bbsVo.subject = 이건 영문이다. 레드선~ 제목을 입력하세요.

NotEmpty.bbsVo.content = 이건 영문이다. 레드선~ 내용을 입력하세요.

각 언어마다 프로퍼티명 끝에 _나라코드 를 입력하면 된다. 만약 한국이라면 message_ko.properties 라고 만들면 된다.

테스트를 위해 강제로 언어를 지정하고 메세지 출력을 확인한다.

ViewController.java 소스를 열어 procBbsWrite 메서드를 확인한다.

String message = messageSource.getMessage(result.getFieldError(), Locale.ENGLISH);

Locale.ENGLISH 를 직접 코딩하여 국적을 변경하였다. 영문 메세지 경고가 출력되는 지 확인한다.



posted syaku blog

Syaku Blog by Seok Kyun. Choi. 최석균.

http://syaku.tistory.com