본문 바로가기

카테고리 없음

Spring 08. 게시글 출력 및 페이징처리와 검색시 검색값 유지시키기

 

@Slf4j// log찍어보기 위한 어노테이션
@Controller // bean객체 등록! (servlet-context.xml 에서 확인가능!)
@SessionAttributes({"loginUser"}) 
@RequestMapping("/board")// 공통주소 설정(현재 컨트롤러 호출시 /spring/board의 경로로 들어오는 모든 url요청을 받아줌)
public class BoardController {
	
	@Autowired
	private BoardService boardService;
	
	//${contextPath}/board/list/C	 // 리액트 => 변수명
	@GetMapping("/list/{boardCode}") // 스프링 => 동적파라미터설정 : {변수명} => boardCode의 값을 받아 매핑
	public String selectList(
			@PathVariable("boardCode") String boardCode
			// @PathVariable(변수명) : URL경로로 포함되어있는 값을 변수로 사용가능
			// 			+ PathVariable로 등록한 변수는 자동으로 requestScope에 저장된다.
			, @RequestParam(value="currentPage", defaultValue = "1" ) int currentPage
			, Model model
			, @RequestParam Map<String, Object> paramMap //요청받은 값을 담아줄 예정
			) {	
		
		paramMap.put("boardCode", boardCode);
		log.info("paramMap = {}", paramMap);
		// @Slf4j어노테이션으로 log찍어볼 수 있음. 2번째 인자값이 1번째 {}안에 값으로 출력됨
		
		
		// 1) 게시글갯수 카운팅(페이징처리)
		int listCount = boardService.selectListCount(paramMap);
		int pageLimit = 10; // 페이징수
		int boardLimit = 5; // 한 페이지에 보여질 게시글수
		
		// 2) pageInfo 생성
		PageInfo pi = Pagination.getPageInfo(listCount, currentPage, pageLimit, boardLimit);
           	// Pagination.java에 미리 생성해놓은 필드명들을 가져옴
		
		// 3) 게시글 목록 조회
		List<Board> list = boardService.selectList(pi, paramMap);
		
		// 4) pageInfo, list, paramMap을 model에 추가(requestScope)
		model.addAttribute("pi", pi);
		model.addAttribute("list", list);
		model.addAttribute("param", paramMap) ;
		
		return "board/boardListView";
	}
}

 

// boardmapper.mxl

// 1)boardWriter가 userNo값을 담고있기 때문에 MEMBER테이블과 JOIN하여 userName값 가져올 예정
// 2)WHERE절에 if문을 통해 검색내용이 있다면 검색한 keyword에 맞는 데이터들만 가져오기 
<select id="selectList" parameterType="map" resultMap="boardResultSet">
    SELECT BOARD_NO, BOARD_TITLE, BOARD_CONTENT, COUNT, CREATE_DATE,
           ORIGIN_NAME, CHANGE_NAME, BOARD_CD, USER_NAME as BOARD_WRITER
      FROM BOARD B
      JOIN MEMBER M ON M.USER_NO = B.BOARD_WRITER
     WHERE B.STATUS = 'Y'
       AND BOARD_CD = #{boardCode}
       <if test="keyword != null and keyword != ''">
            AND
            <choose>
                <when test="condition == 'title'">
                    BOARD_TITLE LIKE '%${keyword}%' 
                </when>
                <when test="condition.equals('content')">
                    BOARD_CONTENT LIKE '%' || #{keyword} || '%'
                </when>
                <when test="condition.equals('writer)">
                    USER_NAME LIKE CONCAT(CONCAT('%', #{keyword}), '%')
                </when>
                <when test="condition.equals('titleAndContent')">
                    (BOARD_TITLE LIKE '%${keyword}%'
                    OR
                    BOARD_CONTENT LIKE '%' || #{keyword} || '%')
                </when>
            </choose>
       </if>
        ORDER BY BOARD_NO DESC
</select>

 

// 게시글 출력하기
// boardListView.jsp 

<div class="innerOuter" style="padding:5% 10%;">
    <h2>일반게시판</h2>

    <c:if test="${not empty loginUser} }" >
        <a class="btn btn-secondeary" style="float:right" href="" >글쓰기</a>
    </c:if>
    <br>

    <table id="boardList" class="table table-hover" align="center">
        <thead>
            <tr>
                <th>글번호</th>
                <th>제목</th>
                <th>작성자</th>
                <th>조회수</th>
                <th>작성일</th>
            </tr>
        </thead>
        <tbody>
            <c:choose>
                <c:when test="${empty list}"> 
                // controller에서 model에 담은 "list"가 없다면
                    <tr>
                        <td colspan="5">게시글이 없습니다.</td>
                    </tr>
                </c:when>
                <c:otherwise>
                // "list"를 boardList라는 변수명으로 DB의 데이터를 뿌려주기
                    <c:forEach var="boardList" items="${list}">
                        <tr>
                            <td>${boardList.boardNo}</td>
                            <td>${boardList.boardTitle}</td>
                            <td>${boardList.boardWriter}</td>
                            <td>${boardList.count}</td>
                            <td>${boardList.createDate}</td>
                        </tr>
                    </c:forEach>
                </c:otherwise>
                    <tr>
                        <td colspan="5">게시글이 없습니다.</td>
                    </tr>
                </c:otherwise>
            </c:choose>
        </tbody>
    </table>

 

// 페이징처리 및 검색기능
// boardListView.jsp

<c:set var="url" value="?currentPage="></c:set> // 공통 url주소를 담음
<c:if test="${not empty param.condition}" >
    <c:set var="searUrl" value="&condition=${param.condition}&keyword=${param.keyword}" />
</c:if>

<div id="pagingArea">
    <ul class="pagination">
        <c:if test="${pi.currentPage eq 1}"> // 1페이지일때  
            <li class="page-item">
            <a class="page-link">Previous</a></li>
        </c:if>
        <c:if test="${pi.currentPage ne 1}"> // 1페이지가 아닐때만 보이게  
            <li class="page-item">
            <a class="page-link" href="${url}${pi.currentPage-1}${searUrl}">Previous</a></li>
        </c:if>

        <c:forEach var='i' begin='${pi.startPage}' end='${pi.endPage}'>
            <li class="page-item">
            <a class="page-link" href="${url}${i}${searUrl}">[ ${i} ]</a></li>
        </c:forEach>

        <c:if test="${pi.currentPage eq pi.maxPage}"> // 마지막페이지일때  
            <li class="page-item">
            <a class="page-link">Next</a></li>
        </c:if>
        <c:if test="${pi.currentPage ne pi.maxPage}"> // 마지막페이지가 아닐때  
            <li class="page-item">
            <a class="page-link" href="${url}${pi.currentPage+1}${searUrl}">Next</a></li>
        </c:if>
    </ul>
</div>


<form id="searchForm" method="get" action="${boardCode}" align="center">
    <div class="select">
        <select class="custom-select" name="condition">
        	// option 체크가 'writer'라면 페이지 변경시에도 검색값이 유지되게 함
            <option value="writer" ${param.condition eq 'writer' ? 'selected' : '' }>작성자</option>
            <option value="title" ${param.condition eq 'title' ? 'selected' : '' }>제목</option>
            <option value="content" ${param.condition eq 'content' ? 'selected' : '' }>내용</option>
            <option value="titleAndContent" ${param.condition eq 'titleAndContent' ? 'selected' : '' }>제목+내용</option>
        </select>
    </div>

    <div class="text">
        <input type="text" class="form-control" name="keyword" value="${param.keyword}"/>
    </div>
    <button type="submit" class="searchBtn btn btn-secondary">검색</button>
</form>

 

// Pagination.java

public class Pagination {
	
	public static PageInfo getPageInfo(int listCount, int currentPage,
			int pageLimit, int boardLimit) {
		
		int maxPage =(int)(Math.ceil(((double)listCount/boardLimit)));
        int startPage = (currentPage-1) / pageLimit * pageLimit+1;
        int endPage = startPage+pageLimit-1;
        
        if(endPage>maxPage) {
            endPage=maxPage;
        }
        
        PageInfo pageinfo = new PageInfo();
        pageinfo.setBoardLimit(boardLimit);
        pageinfo.setCurrentPage(currentPage);
        pageinfo.setEndPage(endPage);
        pageinfo.setListCount(listCount);
        pageinfo.setMaxPage(maxPage);
        pageinfo.setPageLimit(pageLimit);
        pageinfo.setStartPage(startPage);
        
        return pageinfo;
	}
}