2 분 소요

공지사항 페이징

1.순서

1.Criter 클래스/pageDTO클래스 정의 하기

2.Mapper 작성

3.Service 작성

4.Controller 처리

5.view 처리


 

1.Criter 클래스/pageDTO클래스 정의 하기

페이징 쿼리를 동적 제어하기 위해서 필요한 데이터들을 변수로 전달하기 위한 용도로 Criteria 클래스를 작성한다. (동적쿼리: 특정조건 및 상황에 맞춰서 변경되는 쿼리 )

  • Criter 클래스 정의하기

package com.supermm.model;

import lombok.Data;

@Data //lombok
//pageNum과 amount를 같이 파라미터로 전달하기 위한 용도, criteria(기준)
public class Criteria { 
	private int pageNum; //현재페이지
	private int amount; //한페이지당 보여질 게시물 개수	
	

	////////search ///////////
	private String searchType; 
	private String keyWord;
	
	//기본생성자 : 기본세팅(pageNum=1, amount=5)
	public Criteria() {
		this(1, 5);
	}
	
	//생성자 : 원하는 pageNum, amount
	public Criteria(int pageNum, int amount) {
		this.pageNum = pageNum;
		this.amount = amount;
	}
	
	public void setSearchType(String searchType) {
		this.searchType = searchType;
	}
}

해당 클래스는 지정한 개수와 검색조건에 따라서 데이터를 출력하는 쿼리를 실행하는데 필요로 한 데이터들의 모임이다.

(검색 기능은 검색기능 창에서 확인)

 

  • PageDTO 클래스 정의하기

PageDTO는 아래의 사용자가 클릭을 통해 이동할 수 있는 인터페이스이다


package com.supermm.model;

import lombok.Data;

@Data //lombok
public class PageMakeDTO {
   private int startPage; //시작페이지
   private int endPage; //끝페이지
   private boolean prev, next; //이전페이지, 다음페이지 존재유무
   private int total; //전체 게시물 수
   private int realEnd; //전체 마지막페이지
   private int realStart; //전체 시작페이지
   
   private int pageNum; //조회 페이지 번호
   private int amount; //보여질 데이터 개수
   
   private Criteria cri; //현재페이지, 페이지당 게시물 표시수 정보
   //생성자
   public PageMakeDTO(Criteria cri,int total) {
   
      this.cri = cri;
      this.total = total;
      
      //////
      this.pageNum = cri.getPageNum();
      this.amount = cri.getAmount();
      //////
      
      //마지막페이지
      this.endPage = (int)(Math.ceil(cri.getPageNum()/10.0))*10;
      
      //시작페이지
      this.startPage = this.endPage - 9;
      
      //전체 마지막페이지
      this.realEnd = (int)(Math.ceil(total * 1.0/cri.getAmount()));

      //전체 시작페이지
      this.realStart = this.realEnd - (this.realEnd-1);
      
      //전체 마지막페이지(realEnd)가 화면에 보이는 마지막페이지(endPage)보다 작은 경우, 보이는 페이지(endPage)값 조정 (화면에 보일 마지막페이지 유효성 체크)
      if(realEnd < this.endPage) {
         this.endPage = realEnd;
      }
      
      //시작페이지(startPage)값이 1보다 큰 경우 true
      this.prev = this.startPage > 1;
      
      //마지막페이지(endPage)값이 1보다 큰 경우 true 
      this.next = this.endPage < realEnd;
   }
   
   
   
}

2.Mapper 작성

  • NoticeMapper.java
public List<NoticeVO> getNoticePaging(Criteria cri);

목록 쿼리를 실행하는 메서드를 선언한다. 목록페이지는 여러 데이터를 받아야함으로 list자료구조로 반환 받는다.

1. SELECT 결과 하나의 행에 대한 정보만 얻을 경우 VO를 클래스타입으로 받아도 되나 리스트 같이 두개의 행으로 이루 어져 있을 경우 List타입으로 반환 받는다

2. List는 배열과 다르게 삽입되는 데이터에 따라 크기가 동적으로 변한다

list에 저장될 데이터가 NoticeVO임을 명시하기 위해서 NoticeVO 제네릭을 선언한다.

 

	public int getNoticeTotal(Criteria cri);

PageDTO 클래스 생성자를 파라미터로 부여했기 때문에 total이 필요하다.

cri은 이미 정의 되어 있음

total값은 테이블의 총 행의 갯수이다.

갯수를 받아야하므로 int의 리턴타입을 가진다.

keyword의 데이터를 받기 위해서 Criteria 클래스르 부여한다.

  • NoticeMapper.xml

	<!-- 목록페이징 -->
	<select id="getNoticePaging"
		resultType="com.supermm.model.NoticeVO">	
	
	
		  select 
		  nno, ntitle, nwriter_id, ncontent, nregdate, updatedate,nhit
			from(select /*+INDEX_DESC(anotice nno) */
				    rownum rnum, nno, ntitle, nwriter_id, ncontent, nregdate, updatedate, nhit
                from anotice where 
				<include refid="criteria"/>
				<![CDATA[
                rownum <= #{pageNum} * #{amount}]]>
                order by nno)
          		 <![CDATA[where rnum > (#{pageNum} -1) * #{amount}]]>
			   order by nno
	
	</select>


/*+INDEX_DESC(anotice nno) */

인덱스 힌트을 작성하여 공지사항의 번호를 내림차순으로 페이징 처리를 한다.

인덱스 힌트 정리

적절한 인덱스 힌트를 사용하면 쿼리의 수행 속도를 향샹 시킨다

order by를 사용하지 않아도 인덱스의 컬럼 순서가 정렬되어 조회된다

INDEX: 오름차순 / INDEX_DESC : 내림차순

멀티라인 주석과 싱글라인 주석 모두 사용가능

여러개의 복합 인덱스 힌트를 사용가능


<!--공지사항 갯수 -->
	<select id="getNoticeTotal" resultType="int">
		select count(*) from ANOTICE

		<if test="keyWord != null">

			where ntitle like '%'||#{keyWord}||'%'
		</if>
	</select>

총 갯수를 구하기 때문에 count를 사용하였다.

검색조건에 따라서 페이지의 갯수가 바껴야함으로 where를 써 조건문을 쓴다. 적용하지 않으면 페이지 개수보다 더 많은 페이지 번호가 출력된다.

댓글남기기