회원 검색조건
검색 화면
➡️ 기존의 회원 목록에 검색할 수 있는 폼을 만든다. (get방식)
➡️ th:fragment으로 레이아웃 조각을 만든 후 회원 목록 화면에 붙여준다.
🗣 조각을 붙이는 방법
👉🏻 insert vs replace
- insert : 정의된 조각을 삽입하는 방법
ex) <div><div th:insert=”~{페이지 :: 조각이름}”></div></div> 렌더링 시 → <div><div>조각</div></div>
- replace : 선언한 태그와 관련없이 조각으로 교체한다.
ex) <div><div th:replace=”~{페이지 :: 조각이름}”></div></div> 렌더링 시 → <div>조각</div>
[코드]search.html
<!DOCTYPE html> <html lang="en" xmlns:th="http://www.thymeleaf.org"> <div th:fragment="searchFragment"> <form th:action="@{/member/memberList}" method="get"> <select name="searchKey"> <option value="memberId">회원아이디</option> <option value="memberName">회원이름</option> <option value="memberEmail">회원이메일</option> </select> <input type="text" name="searchValue" placeholder="검색어를 입력해주세요."> <button type="submit">검색</button> </form> </div> </html>
[코드]memberList.html
<!DOCTYPE html> <html xmlns:th="http://www.thymeleaf.org" xmlns:layout="http://www.ultraq.net.nz/thymeleaf/layout" layout:decorate="~{layout/default}"> <head> <link rel="stylesheet" type="text/css" th:href="@{/css/table.css}"> </head> <th:block layout:fragment="customContents"> // 컨텐츠 레이아웃 조각내에 searchFragment 조각 삽입 <div th:insert="~{fragments/search :: searchFragment}"></div> /* 코드 생략 */ </th:block> </html>
➡️ 기존의 회원목록을 주소 요청 하는 메소드에 매개변수 값으로 searchKey, searchValue 을 받는다.
➡️ 전달받은 데이터를 기존 Service 메소드의 호출하는 곳으로 넘겨준다.
[코드]Controller.java
/** * 회원목록 조회 * @param model * @return */ @GetMapping("/memberList") public String getMemberList(Model model, @RequestParam(value="searchKey", required = false, defaultValue = "") String searchKey, @RequestParam(value="searchValue", required = false) String searchValue) { // lombok - 콘솔에 해당 값을 보여준다. log.info("searchKey : {}", searchKey); log.info("searchValue : {}", searchValue); List<Member> memberList = memberService.getMemberList(searchKey, searchValue); model.addAttribute("title", "회원목록"); model.addAttribute("memberList", memberList); return "member/memberList"; }
➡️ 1) 기존 회원목록을 조회하는 메소드의 매개변수에 컨트롤러에서 전달받은 데이터를 넣어준다.
2) 전달받은 데이터 중 searchKey를 해당 DB 컬럼명과 일치 시키기 위해 로직을 작성한다. (searchValue가 null이 아닐때)
3) 그 후 map에 searchKey와 searchValue를 담아주고, 기존 mapper에 회원목록을 조회하는 메소드를 호출한 곳의 매개변수에 던져준다.
👉🏻 모든 타입을 담을 수 있는 구조 : dto, map
[코드]Service.java
// 회원목록 조회 public List<Member> getMemberList(String searchKey, String searchValue) { // map 구조 생성 Map<String, Object> paramMap = null; if(searchValue != null) { switch (searchKey) { case "memberId" -> { searchKey = "m_id"; } case "memberName" -> { searchKey = "m_name"; } case "memberEmail" -> { searchKey = "m_email"; } } paramMap = new HashMap<String, Object>(); paramMap.put("searchKey", searchKey); paramMap.put("searchValue", searchValue); } List<Member> memberList = memberMapper.getMemberList(paramMap); /* 코드 생략 */ return memberList; }
➡️ 기존에 회원목록을 조회했던 쿼리에서 parameterType=”map” 을 추가해준다. (인터페이스 mapper 매개변수에 map이 담긴다.)
➡️ where 조건절은 동적쿼리를 사용해서 처리한다. (검색 조건)
👉🏻 <where> 태그 사용 → 동적쿼리 (파라미터 값이 있을 경우에만 실행된다.)
LIKE → 문자열의 내용을 검색, %기호는 그자리에 어떤 값이 들어와도 상관 없다는 의미이다.
CONCAT(str1, str2) → 문자열 연결
👉🏻 ${} vs #{}
- ${} (Statement) → ${m_id} 쿼리문에서는 m_id
- #{} (PreparedStatement) → #{m_id} 쿼리문에서는 ‘m_id’
[코드]Mapper.xml
<select id="getMemberList" parameterType="map" resultType="Member"> /* 회원목록 조회 */ SELECT m.m_id AS memberId, m.m_pw AS memberPw, m.m_name AS memberName, m.m_level AS memberLevel, m.m_email AS memberEmail, m.m_addr AS memberAddr, m.m_reg_date AS memberRegDate FROM tb_member AS m <where> <if test="searchValue != null and searchValue != ''"> ${searchKey} Like CONCAT('%', #{searchValue}, '%') </if> </where> </select>
[코드]Mapper.java
// 회원목록 조회 public List<Member> getMemberList(Map<String, Object> paramMap);
tag : #Spring #Mybatis #Controller #Service #Mapper #동적쿼리 #map #fragment
Uploaded by N2T