Spring

타임리프 - 스프링 통합과 폼 : 체크박스, 라디오버튼, 셀렉트 박스

sami355 2022. 8. 24. 14:05

인프런 김영한님의 스프링mvc2편을 보고 정리한 글입니다.

무엇을 배웠나요?

  • html에서 체크박스를 체크하면html Form에서 on이라는 값이 넘어간다. 이때 스프링은 on이라는 문자를true타입으로 변환해준다. (by 스프링타입 컨버터)💡이때 스프링은 체크박스의 이름 앞에 언더스코어(_)를 만들어서 전송을 하면 체크를 해제했다고 인식할 수 있다
  • ⚠️ HTML에서 체크 박스를 선택하지 않고 폼을 전송하면 타임리프에서 생성한 필드 자체가 서버로 전송되지 않는다. 즉 서버에서는 null로 처리한다. 이때 만약 수정을 하려고 하는 경우 상황에 따라서 문제가 될수도 있다.(체크 되어있는 것을 해제하고 서버로 전송해버리면 서버로는 아무값도 넘어가지 않기 때문에 값이 수정 되지 않을 수도 있다.)
ex) open과 _open 중 _open만 전송되면 체크를 해제했다고 판단.
<!-- single checkbox -->
<div>판매 여부</div>
<div>
 <div class="form-check">
 <input type="checkbox" id="open" class="form-check-input" name="open"
value="true">
 <input type="hidden" name="_open" value="on"/>
 <label for="open" class="form-check-label">판매 오픈</label>
 </div>
</div>

-> 타임리프가 히든 필드를 생성해준다.

 

  • th:field를 사용하면 타임리프가 체크 박스 코드를 제공해준다.
  • 체크박스에서 th:field의 값이 T/F이면 타임리프가 자동으로 속성을 추가해 처리해준다.
    <!-- single checkbox -->
    <div class="form-check">
     <input type="checkbox" id="open" class="form-check-input" disabled
    name="open" value="true"
     checked="checked">
     <label for="open" class="form-check-label">판매 오픈</label>
    </div>
    
  • <!-- single checkbox --> <div> <div class="form-check"> <input type="checkbox" id="open" th:field="${item.open}" class="formcheck-input" disabled> <label for="open" class="form-check-label">판매 오픈</label> </div>
  • 만약 여러 컨트롤러에서 동일한 데이터를 동일하게 작업해준다면 @ModelAttribute를 이용하면 해당 컨트롤러를 요청할때 자동으로 Model에 담기게 된다.
  • @ModelAttribute("regions") public Map<String, String> regions() { Map<String, String> regions = new LinkedHashMap<>(); regions.put("SEOUL", "서울"); regions.put("BUSAN", "부산"); regions.put("JEJU", "제주"); return regions; }
  • 타임리프가 같은 이름의 체크박스를 만들때(each를 이용해서 동적으로) HTML태그 속성에서 id가 동일하면 안되기 때문에 타임리프는 each루프 안에서 임의로 숫자를 붙여준다.
  • each를 이용해서 동적으로 태그들을 만드는 상황에서 for속성을 이용해서 id를 명시해야 할 필요가 있다면 타임리프는 ids.prev(…), ids.next(…)을 제공해서 동적으로 생성되는 id값을 사용할 수 있도록 한다.
    <input type="checkbox" value="SEOUL" class="form-check-input" id="regions1"
    name="regions">
    <input type="checkbox" value="BUSAN" class="form-check-input" id="regions2"
    name="regions">
    <input type="checkbox" value="JEJU" class="form-check-input" id="regions3"
    name="regions">
    
  • <!-- multi checkbox --> <div> <div>등록 지역</div> <div th:each="region : ${regions}" class="form-check form-check-inline"> <input type="checkbox" th:field="*{regions}" th:value="${region.key}" class="form-check-input"> <label th:for="${#ids.prev('regions')}" th:text="${region.value}" class="form-check-label">서울</label> </div> </div>
  • 멀티 체크 박스에서 등록 지역을 선택해서 저장하면, 조회시에 checked속성이 추가된 것을 확인 할 수 있다. → th:field에 지정한 값과 th:value의 값을 비교해서 체크를 자동으로 처리해준다.
  • <!-- multi checkbox --> <div> <div>등록 지역</div> <div th:each="region : ${regions}" class="form-check form-check-inline"> <input type="checkbox" th:field="${item.regions}" th:value="$ {region.key}" class="form-check-input" disabled> <label th:for="${#ids.prev('regions')}" th:text="${region.value}" class="form-check-label">서울</label> </div> </div>
  • 라디오 버튼은 ,체크박스와는 다르게, 이미 선택 되어 있다면, 수정시에도 항상 하나를 선택하도록 되어 있으므로 별도의 히든 필드를 사용할 필요가 없다.
  • enum으로 데이터를 넘겨주면 타임리프는 자바객체에 직접 접근할 수 있다.
  • <!-- radio button --> <div> <div>상품 종류</div> <div th:each="type : ${itemTypes}" class="form-check form-check-inline"> <input type="radio" th:field="*{itemType}" th:value="${type.name()}" class="form-check-input"> <label th:for="${#ids.prev('itemType')}" th:text="${type.description}" class="form-check-label"> BOOK </label> </div> </div>

기타

  • html문법에서 for속성은 특정 요소id에 붙히기 위해서 사용