자바(JAVA)/JSP 웹 프로그래밍 공부 (성낙현의 JSP 자바 웹 프로그래밍 참고)
JAVA/JSP 28. 회원제 게시판에 페이징 기능 추가 - 페이징이 필요한 이유, 페이징 구현 절차
개발학생
2025. 4. 15. 15:51
반응형
1. 페이징이 필요한 이유
*기존 회원제 게시판의 게시물이 1만 개가 되었다고 할 때의 문제점
⇒ 이래서 게시판에서는 게시글 목록을 보통 10~20개 정도씩 나눠 페이지별로 출력하는 것(=페이징)
(1) 스크롤이 길어져서, 사용자가 목록에서 원하는 게시글을 찾기 어려움(가독성 저하)
(2) 전송해야 할 데이터가 많아지므로, 페이지 로딩 속도가 느려짐
(3) 한 페이지에서 한꺼번에 많은 데이터를 처리해야 하므로, 데이터베이스에 과부하가 걸림
2. 페이징 구현 절차
1) 페이징 구현 이전 기본 설정값
(1) 한 페이지에 출력할 게시물의 개수 (레코드의 범위)
- POSTS_PER_PAGE=10
(2) 한 화면(블록)에 출력할 페이지 번호의 개수
- PAGES_PER_BLOCK=5
2) 페이징 구현 단계
(1) board 게시물에 저장된 전체 레코드 수 카운트
- 계산 예: 전체 게시물을 105개라고 가정
(2) 각 페이지에서 출력할 게시물의 범위 계산
- 계산식
- 범위의 시작값: (현재 페이지 - 1) * POSTS_PER_PAGE + 1
- 범위의 종료값: (현재 페이지 * POSTS_PER_PAGE)
- 계산 예
- 현재 1페이지일 때: 시작값 (1-1)10+1=1, 종료값 110=10
- 현재 2페이지일 때: 시작값 (2-1)10+1=11, 종료값 210=20
(3) 전체 페이지 수 계산 - 계산된 결과는 무조건 올림 처리
→ 올림 처리를 안 하면 마지막 페이지의 게시물 5개 조회 불가
- 계산식: Math.ceil(전체 게시물 수 / POSTS_PER_PAGE)
- 계산 예: 게시물 수가 총 105개일 경우
- 페이지 수: Math.ceil(105 / 10) = Math.ceil(10.5) = 11
(4) ‘이전 페이지 블록 바로가기’ 출력
- 계산식: ((현재 페이지 - 1) / PAGES_PER_BLOCK) * PAGES_PER_BLOCK + 1
- 계산 예 → pageTemp가 1일때는 이전 페이지 목록 바로가기를 출력하지 않음 → pageTemp가 1 이상일 때는 pageTemp - 1 페이지 블록 바로가기를 출력함
- 현재 1페이지일 때: pageTemp = ((1-1) / 5) * 5 + 1 = 1
- 현재 5페이지일 때: pageTemp = ((5-1) / 5) * 5 + 1 = 5
(5) 각 페이지 번호를 출력
- 앞에서 계산한 pageTemp를 BLOCK_PAGE만큼 반복하면서 +1 연산 후 출력
- 계산 예
- pageTemp가 1일 때: “1 2 3 4 5”를 출력
- pageTemp가 6일 때: “6 7 8 9 10”을 출력
(6) ‘다음 페이지 블록 바로가기’ 출력
- 각 페이지 번호를 출력한 후, pageTemp + 1하여 다음 페이지 블록 바로가기 설정
- → 마지막 페이지 번호가 5라면, 다음 페이지 블록은 6이 됨
페이징 구현 실습
더미 데이터 입력
- 페이징 기능을 테스트하려면 데이터가 많이 입력되어 있어야 하므로, 반복문을 이용해서 더미 데이터 100개를 한 번에 삽입
→ 게시글을 하나씩 수동으로 채워 넣는 방법도 있지만, 다수의 데이터를 입력하려면 귀찮고 시간도 오래 걸리기 때문
WebContent → PagingBoard의 WriteProcess.jsp 파일을 열어 코드 수정
// WebContent/PagingBoard/WriteProcess.jsp
... 생략 ...
//DAO 객체를 통해 DB에 DTO 저장
BoardDAO dao = newBoardDAO(application);
//int iResult = dao.insertWrite(dto); //원래 코드
//2.
int iResult = 0;
for (int i = 1; i <= 100; i++) {
dto.setTitle(title + "-" + i); //3.
iResult = dao.insertWrite(dto);
}
dao.close();
... 생략 ...
- Write.jsp 파일 실행 후 글을 작성한 결과
페이징용 쿼리문 작성
- 사용하는 DBMS가 오라클이므로, rownum을 이용해서 쿼리문을 작성함
*rownum이란?
- 오라클에서 생성된 모든 테이블에서 사용할 수 있는, 가상의 컬럼 → SELECT 쿼리문으로 추출하는 데이터(row)에 순차적으로 부여되는 순번(num)
- 물리적으로 존재하는 컬럼이 아니므로, 값을 변경하기 위한 DML문(INSERT, UPDATE, DELETE)은 사용 불가
**실습
1. 명령 프롬프트(cmd) 실행
2. sqlplus 명령으로 오라클에 접속 (username: hello, pw:1234) → sql을 입력할 수 있는 상태가 됨
3. DESC 명령어로 member 테이블의 구조 확인 → 컬럼이 4개인 것을 확인할 수 있음
4. SELECT문으로 member 테이블의 모든 레코드 읽어오기
5. SELECT문에 id, pass 컬럼을 지정하고 rownum 사용 → rownum 컬럼을 만들지 않았음에도, rownum 컬럼에 순번이 출력됨
페이징 처리용 쿼리문 작성
- 이전 28번 정리글의 ‘페이징 구현 절차’에서 게시물을 카운트하여 각 페이지에서 출력할 게시물의 범위를 계산했고, 그 결과에서 범위의 시작값과 끝값을 구함 → 이 시작값과 끝값을 이용해, CMD에 쿼리문 작성
첫 번째 페이지에 출력할 게시물
- 총 10개의 게시물이 출력되는데, 화면이 너무 길어 두 번째 행부터는 생략 → 2페이지에 해당하는 행을 가져오고 싶다면, BETWEEN문의 값을 11~20까지로 변경
- 매개변수를 이용해서 페이지별 목록의 범위를 계산하고, DAO에서 이를 적용한 쿼리문을 실행한 결과를 반환하면 됨
SELECT * FROM ( //3.(괄호 밖의 WHERE 절까지 포함)
SELECT Tb.*, rownum rNum FROM ( //2.(괄호 밖의 'tb'까지 포함)
SELECT * FROM board ORDER BY num DESC //1.
) tb
)
WHERE rNum BETWEEN 1 and 10;
- board 테이블의 모든 게시물을 일련번호(num)에 대해 내림차순으로 정렬해서 가져옴
- 1번 쿼리문의 결과문을 *를 통해 모두 가져오고, rownum을 추가하여 순번 부여 → rownum 컬럼에는 별칭 rNum 사용
- 첫 페이지에 출력할 게시물 범위가 1~10이므로, rownum으로 부여한 번호를 이용해 구간을 정해 가져올 수 있음 → WHERE 절에서는 구간을 정하는 것이므로, BETWEEN 대신 rNum >=과 같이 조건을 부여할 수도 있음
반응형