728x90
🔔 TODO : 페이징 , 게시글 AJax수정, 삭제
📘 project : 인텔리제이 - SpringBootMybatisMini
github : https://github.com/Hyeonqz/SpringBootMybatisMini
스프링부트 동작관정 간단
- 클라이언트가 JSP 페이지에 데이터를 입력하고 제출합니다.
- JSP 페이지에서 컨트롤러에게 요청을 보냅니다.
- 컨트롤러는 요청을 받고 필요한 작업을 수행합니다.
- 컨트롤러는 서비스로 데이터 처리를 위임합니다.
- 서비스는 필요한 비즈니스 로직을 실행하고 데이터베이스에서 데이터를 가져옵니다.
- 서비스가 데이터 처리를 완료하면, 결과를 컨트롤러로 반환합니다.
- 컨트롤러는 JSP 페이지로 데이터를 전달합니다.
- JSP 페이지는 데이터를 이용하여 동적 웹 페이지를 생성하고 클라이언트에게 반환합니다.
따라서 데이터 처리 후 반환되는 곳은 컨트롤러이다.
페이징을 해보겠습니다.
1) mapper
<select id="getList" parameterType="HashMap" resultType="MemboardDto">
select * from memboard order by num desc limit #{start},#{perpage}
</select>
- mysql -> limit 를 알아야지 페이징을 할 수 있습니다.
- limit는 (begin, end)로 구성되며 (시작페이지부터, 마지막 페이지) 즉 내가 설정해둔 시작페이지부터 내가설정해둔 마지막페이지 까지 제한 한다는 뜻 입니다.
2) service
@Override
public List<MemBoardDto> getList(int start, int perpage) {
HashMap<String,Integer> map = new HashMap<>();
map.put("start",start);
map.put("perpage",perpage);
return memBoardMapperInter.getList(map);
}
- 페이징을 하기 위해서 Map 컬렉션에 start, perpage를 담아서 dto값 , map을 list에 리턴합니다
3) controller
@GetMapping("/list")
public ModelAndView goreboard(
@RequestParam(value="currentPage",defaultValue = "1") int currentPage) {
ModelAndView mv= new ModelAndView();
int totalCount = memboardService.getTotalCount();
//페이징 처리 필요한 변수 선언
int totalPage; //총 페이지수
int startPage; //각블럭에서 보여질 시작페이지
int endPage; //각블럭에서 보여질 끝페이지
int startNum; //db에서 가져올 글의 시작번호(mysql은 첫글이 0,오라클은 1)
int perPage=10; //한페이지당 보여질 글의 갯수
int perBlock=5; //한블럭당 보여질 페이지 개수
//현재페이지 읽기(단 null일경우는 1페이로 준다)계산을 해야하므로 int로 형변환해줌
//if(("currentPage")==null)
// currentPage=1;
//else
//currentPage=Integer.parseInt(("currentPage"));
//총페이지수 구하기
//총글의 갯수/한페이지당 보여질 개수로 나눔(7/5=1)
//나머지가 1이라도 있으면 무조건 1페이지 추가(1+1=2페이지가 필요)
totalPage=totalCount/perPage+(totalCount%perPage==0?0:1);
//각블럭당 보여야할 시작페이지
//perBlock=5일경우는 현재페이지 1~5 시작:1 끝:5
//현재페이지 13 시작:11 끝:15
startPage=(currentPage-1)/perBlock*perBlock+1;
endPage=startPage+perBlock-1;
// 총페이지가 23일경우 마지막블럭은 25가아니라 23이다
if(endPage>totalPage)
endPage=totalPage;
//각페이지에서 보여질 시작번호
//1페이지: 0,2페이지:5 3페이지:10....
startNum=(currentPage-1)*perPage;
//각 페이지에서 필요한 게시글 가져오기 == 보여질 글만 가져오기
//각페이지당 출력할 시작번호 구하기 no
//총글개수가 23이면 1페이지 23,2페이지는 18,3페이지 13.....
//출력시 1씩 감소하며 출력
List<MemBoardDto> list = memboardService.getList(startNum, perPage);
//list의 각 글에 댓글 개수 표시를 해야함
/*for(MemBoardDto m:list) {
m.setAcount(adao.getAnswerList(d.getNum()).size());
}*/
//각 페이지에 출력할 시작번호
int no = totalCount-(currentPage-1)*perPage;
mv.addObject("totalCount",totalCount);
mv.addObject("list",list);
mv.addObject("startPage",startPage);
mv.addObject("totalPage",totalPage);
mv.addObject("endPage",endPage);
mv.addObject("no",no);
mv.addObject("currentPage",currentPage);
mv.setViewName("/memboard/memlist");
return mv;
}
- form 에 보낼 때, 보내줄 값이 많기 때문에 ModelandView를 리턴타입으로 사용해서 보내준다.
- totalCount는 모든 dto들을 list로 출력하기 위해서 생성한 변수 이다.
- 그리고 페이징 처리에 필요한 변수들을 미리 선언해줍니다
- 자세한 설명들은 코드에 주석으로 설명되어 있습니다.
- 그리고 컨트롤러에서 addObject 메소드 안에있는 key값들은 jsp파일에서 직접적으로 사용할 수 있습니다.
4) form 작성
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<link href="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0/dist/css/bootstrap.min.css" rel="stylesheet">
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap-icons@1.11.1/font/bootstrap-icons.css">
<link href="https://fonts.googleapis.com/css2?family=VT323&display=swap" rel="stylesheet">
<script src="https://code.jquery.com/jquery-3.7.0.js"></script>
<title>회원 게시판</title>
</head>
<body>
<div style="width: 1150px;">
<c:if test="${sessionScope.loginok != null}">
<button type="button" class="btn btn-outline-info" onclick="location.href='form'" style="width:100px;">글쓰기</button>
</c:if>
<br><br>
<table class="table table-bordered">
<tr class="table-secondary" align="center">
<th width="60">번호</th>
<th width="60">제목</th>
<th width="60">작성자</th>
<th width="60">조회수</th>
<th width="60">등록일</th>
</tr>
<c:if test="${totalCount==0}">
<tr>
<td>등록된 글이 없습니다.</td>
</tr>
</c:if>
<c:if test="${totalCount>0 }">
<c:forEach var="dto" items="${list }" varStatus="i">
<tr>
<td align="center">${no }</td>
<c:set var="no" value="${no-1 }"/> <!-- 출력 후 감소시키기 -->
<td> <!-- 제목 -->
<!-- 제목.. 여기 누르면 내용 보기로 -->
<a href="content?num=${dto.num }¤tPage=${currentPage}">${dto.subject }</a>
<!-- 사진이 있을 경우 아이콘 표시 -->
<c:if test="${dto.uploadfile != 'no' }">
<i class="bi bi-image"></i>
</c:if>
</td>
<td><fmt:formatDate value="${dto.writeday }" pattern="yyyy-MM-dd"/></td>
<td align="center">${dto.readcount }</td>
</tr>
</c:forEach>
</c:if>
</table>
<!-- 페이지번호 출력 -->
<!-- 페이지 번호 출력 -->
<div>
<!-- 페이지 번호 출력 -->
<c:if test="${totalCount>0 }">
<div style="width: 800px; text-align: center">
<ul class="pagination justify-content-center">
<!-- 이전 -->
<c:if test="${startPage>1 }">
<li class="page-item"><a class="page-link" href="list?currentPage=${startPage-1 }">이전</a></li>
</c:if>
<c:forEach var="pp" begin="${startPage }" end="${endPage }">
<c:if test="${currentPage==pp }">
<li class="page-item active"><a class="page-link"
href="list?currentPage=${pp }">${pp }</a></li>
</c:if>
<c:if test="${currentPage!=pp }">
<li class="page-item"><a class="page-link" href="list?currentPage=${pp }">${pp }</a></li>
</c:if>
</c:forEach>
<!-- 다음 -->
<c:if test="${endPage<totalPage }">
<li class="page-item"><a class="page-link"
href="list?currentPage=${endPage+1 }">다음</a></li>
</c:if>
</ul>
</div>
</c:if>
</div>
</div>
</table>
</div>
</body>
</html>
- totalCount -> 즉 글의 개수가 없으면, 글이 없습니다. 라고 뜨고, totalCount 1 이상있으면 리스트로 나열한다.
- JSTL 태그를 사용해서, c:for each문을 사용해서 list를 출력해줍니다.
지적 감사하게 받겠습니다
728x90