게시판 목록가기, 페이징 처리 구현

·2024년 11월 6일

스프링

목록 보기
14/33
post-thumbnail

이클립스에서 boardList, SearchCriteria, PageMaker, Criteria 전부 가져오기
패키지 이름이 다르니까 고쳐주기

<a href ="<%=request.getContextPath()%>/board/boardList.aws">게시판 목록가기</a>
1. 인덱스 페이지에 경로 추가하기



package com.myaws.myapp.controller;

import java.util.ArrayList;


@Controller
@RequestMapping(value="/board/")
public class BoardController {
	
	
	private static final Logger logger = LoggerFactory.getLogger(BoardController.class);
	
	// BoardService 타입의 객체를 자동으로 주입. 주입 실패 시에도 에러가 발생하지 않고 null로 설정됨
	@Autowired(required = false) 
	private BoardService boardService;
	
	// PageMaker 객체를 자동으로 주입하여 페이지 정보를 설정
	@Autowired(required = false) 
	private PageMaker pm;
	
	
	//게시글 목록을 조회하고 검색 조건에 맞는 게시글을 화면에 표시하는 메서드
	@RequestMapping(value="boardList.aws", method=RequestMethod.GET)
	public String boardList(SearchCriteria scri, Model model) {
		
		// 총 게시글 수를 검색 조건(scri)을 기준으로 조회
		int cnt = boardService.boardTotalCount(scri);
		// PageMaker 객체에 검색 조건과 총 게시글 수를 설정하여 페이지 네비게이션을 준비
		pm.setScri(scri);
		pm.setTotalCount(cnt);
			
		// boardService에서 주어진 검색 조건(scri)을 기반으로 게시글 목록을 조회
		ArrayList<BoardVo> blist = boardService.boardSelectAll(scri);
		
		// 조회된 게시글 목록을 "blist"라는 이름으로 모델에 추가하여 JSP 뷰 페이지로 전달
		model.addAttribute("blist",blist);
		// PageMaker 객체도 모델에 추가하여 JSP 뷰에서 페이지 정보도 접근할 수 있도록 설정
		model.addAttribute("pm",pm);
			
		//경로에 해당하는 JSP 뷰 페이지를 반환
		return "WEB-INF/board/boardList";
		}

}

2. BoardController 생성해서 메서드 생성



package com.myaws.myapp.service;

import java.util.ArrayList;

import com.myaws.myapp.domain.BoardVo;
import com.myaws.myapp.domain.SearchCriteria;

public interface BoardService {
	
	public ArrayList<BoardVo> boardSelectAll(SearchCriteria scri);
	
	public int boardTotalCount(SearchCriteria scri);

}

3.BoardService 생성하기



package com.myaws.myapp.service;

import java.util.ArrayList;
import java.util.HashMap;

import org.apache.ibatis.session.SqlSession;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.myaws.myapp.domain.BoardVo;
import com.myaws.myapp.domain.SearchCriteria;
import com.myaws.myapp.persistance.BoardMapper;



@Service
public class BoardServiceImpl implements BoardService {

	// BoardMapper 타입의 객체 생성 (MyBatis와 연동)
	private BoardMapper bm;
	
	
	
	@Autowired  // SqlSession 객체를 주입받는 생성자
	public BoardServiceImpl(SqlSession sqlSession) {
		// 주입받은 sqlSession 객체를 이용하여 BoardMapper를 초기화
		this.bm = sqlSession.getMapper(BoardMapper.class); /* 꼭 뒤에 클래스가 붙어야한다. */ 
	}
	
	
	
	// 게시글 목록을 검색 조건에 따라 조회하는 메서드
	@Override
	public ArrayList<BoardVo> boardSelectAll(SearchCriteria scri) {
		
		// HashMap 객체를 생성하여 페이징, 검색 타입, 키워드 등의 조건을 추가
		HashMap<String,Object> hm = new HashMap<String,Object>();
		hm.put("startPageNum",(scri.getPage()-1)* scri.getPerPageNum()); // 시작 페이지 번호
		hm.put("searchType", scri.getSearchType());  // 검색 유형
		hm.put("keyword", scri.getKeyword()); // 검색 키워드
		hm.put("perPageNum", scri.getPerPageNum()); // 페이지당 게시글 수
		
		// BoardMapper를 사용해서 검색 조건에 맞는 게시글 목록 조회
		ArrayList<BoardVo> blist = bm.boardSelectAll(hm);
		return blist;
	}

	
	// 총 게시글 수를 검색 조건에 따라 가져오는 메서드
	@Override
	public int boardTotalCount(SearchCriteria scri) {
		// 검색 조건을 통해 BoardMapper에서 총 게시글 수를 조회		
		int cnt = bm.boardTotalCount(scri);
		return cnt;
	}
}

4. BoardServiceImpl 생성하기



package com.myaws.myapp.persistance;

import java.util.ArrayList;
import java.util.HashMap;

import com.myaws.myapp.domain.BoardVo;
import com.myaws.myapp.domain.SearchCriteria;

public interface BoardMapper {
	
	/* 마이바티스용 메소드. 서비스에 있는 메소드 이름을 동일하게 해서 헷갈리지 않게 한다. */ 
	public ArrayList<BoardVo> boardSelectAll(HashMap<String,Object> hm);
	public int boardTotalCount(SearchCriteria scri);

}


5. BoardMapper 생성

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">

<!-- Mapper의 네임스페이스 설정. 해당 인터페이스와 정확히 연결하기 위해 사용-->
<mapper namespace="com.myaws.myapp.persistance.BoardMapper">

 <!-- 검색 필터링을 위한 SQL 구문 정의 -->
<sql id ="search">
  <!-- 검색 조건이 'writer'일 경우 -->
<if test="searchType != null and searchType.equals('writer')"> <!-- 작성자 검색어 포함 -->
	and writer like concat('%',#{keyword},'%')
</if>

 <!-- 검색 조건이 'subject'일 경우 -->
<if test="searchType != null and searchType.equals('subject')"> <!-- 제목 검색어 포함 -->
	and subject like concat('%',#{keyword},'%')
</if>
</sql>


  <!-- 게시글 목록 조회 쿼리 -->
<select id="boardSelectAll" parameterType="HashMap" resultType="bv">
select * from board where delyn='N' <!-- 삭제되지 않은 게시글만 조회 -->
<include refid="search"/> <!-- 검색 필터링 조건 포함 -->
order by originbidx desc, depth asc limit #{startPageNum}, #{perPageNum} <!-- 페이징 처리 -->
</select>



   <!-- 게시글 총 개수를 조회하는 쿼리 -->
<select id ="boardTotalCount" parameterType="scri" resultType="int">
select count(*) as cnt from board where delyn='N'
<include refid="search"/> <!-- 검색 필터링 조건 포함 -->
</select>


</mapper>

6. boardMapper.xml 생성하기



 <typeAlias alias="bv" type="com.myaws.myapp.domain.BoardVo"/>
 <typeAlias alias="scri" type="com.myaws.myapp.domain.SearchCriteria"/>

7. mybatis_config.xml에서 추가해주기



<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@page import = "java.util.*" %>
<%@ page import="com.myaws.myapp.domain.*" %>
    
 <%
 ArrayList<BoardVo> blist = (ArrayList<BoardVo>)request.getAttribute("blist");
 //System.out.println("blist==>" + blist);
 PageMaker pm = (PageMaker)request.getAttribute("pm"); //2-39. 뭐야...
 
 // 게시물 목록 순서 나타내기 
 int totalCount = pm.getTotalCount();  //전체갯수를 뽑아왔어 
 
 String keyword = pm.getScri().getKeyword();
 String searchType = pm.getScri().getSearchType();
 
 String param = "keyword="+keyword+"&searchType="+searchType+""; 
 %>   
    
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>글목록</title>
<link href="/resources/css/style2.css" rel="stylesheet">
</head>
<body>
<header>
	<h2 class="mainTitle">글목록</h2>
	<form class="search" name="frm" action="<%=request.getContextPath()%>/board/boardList.aws" method="get">
		<select name = "searchType">  <!-- 어떤걸 선택할래? -->
			<option value = "subject">제목</option>
			<option value = "writer">작성자</option>
		</select>
		<input type="text" name ="keyword"> <!-- 나는 키워드로 입력할거야  -->
		<button type="submit" class="btn">검색</button>
	</form>
</header>

<section>	
	<table class="listTable">
		<tr>
			<th>No</th>
			<th>제목</th>
			<th>작성자</th>
			<th>조회</th>
			<th>추천</th>
			<th>날짜</th>
		</tr>   <!--스크립틀릿 : 서버에서 실행될 Java 코드를 JSP 페이지에 삽입하여 동적으로 HTML을 생성하는 역할 -->
		<% int num = totalCount - (pm.getScri().getPage()-1)*pm.getScri().getPerPageNum();  // 전체갯수중에 15개를 빼면??
		for(BoardVo bv : blist) { //23. 향상된 for문. blist라는 리스트를 순회하면서 각 요소를 변수에 담아 반복 작업을 수행 
		 
			String lvlStr = ""; // 초기화 
			for(int i=1; i<=bv.getLevel_(); i++) {
				lvlStr = lvlStr + "&nbsp;&nbsp;"; // html에서 띄어쓰기 기호
				if(i == bv.getLevel_()) { // i가 level과 같으면     // level이 증가하면 칸을 옮기고 ㄴ자를 표시해라. 
					lvlStr = lvlStr + "ㄴ"; // ㄴ자 표시를 해준다. 
				}
			}
			
		%> 
		<tr>
			<td><%=num %></td>
			<td class="title">
			<%=lvlStr %>
			<a href="<%=request.getContextPath() %>/board/boardContents.aws?bidx=<%=bv.getBidx() %>"><%=bv.getSubject() %></a></td>
			<td><%=bv.getWriter() %></td>
			<td><%=bv.getViewcnt()%></td>
			<td><%=bv.getRecom()%></td>
			<td><%=bv.getWriteday() %></td>
		</tr>
		<%
		 num = num-1;
		}
		%>
	
	</table>
	
	<div class="btnBox">
		<a class="btn aBtn" href="<%=request.getContextPath() %>/board/boardWrite.aws">글쓰기</a>
	</div>
	
	 <!--  2-40. 이거 다 하면 보드Dao로 가세요 -->
	<div class="page">
		 <ul>
		<%if (pm.isPrev()==true) { %>
		<li><a href="<%=request.getContextPath()%>/board/boardList.aws?page=<%=pm.getStartPage()-1%>&<%=param%>"></a></li>
		<% } %>
		
		<% for(int i = pm.getStartPage(); i<=pm.getEndPage(); i++) { %>  
			<li <%if (i==pm.getScri().getPage()) {%> class="on"<%}%> > 
			<a href="<%=request.getContextPath()%>/board/boardList.aws?page=<%=i%>&<%=param%>"><%=i%> <!-- 해당 검색어가 있으면 그 다음페이지에도 있어야 하니까? -->
			</a>
			</li>
			<% }%>
	
		<%if(pm.isNext()==true && pm.getEndPage()>0){ %>
		<li><a href="<%=request.getContextPath()%>/board/boardList.aws?page=<%=pm.getEndPage()+1%>&<%=param%>"></a></li>
	 	<% } %> 
		</ul> 
	</div>
</section>

</body>
</html>

8. boardList.jsp


HashMap

HashMap은 Java의 java.util 패키지에 있는 클래스 중 하나로, 키-값 쌍으로 데이터를 저장하는 자료구조입니다. HashMap은 다음과 같은 특징을 가지고 있습니다:

키-값 쌍 저장: 각 데이터는 고유한 키와 그에 대응하는 값으로 저장됩니다. 키를 통해 빠르게 값을 검색할 수 있습니다.

중복 키 허용하지 않음: 동일한 키를 가진 값을 추가하면 기존의 값이 새로운 값으로 덮어씌워집니다.

null 허용: HashMap은 null 키와 null 값을 허용합니다. 다만, null 키는 하나만 저장할 수 있습니다.

정렬되지 않은 순서: HashMap은 데이터가 저장된 순서나 특정 기준에 따라 정렬되지 않으며, 해시 함수에 의해 위치가 결정됩니다.

비동기적: 기본적으로 HashMap은 스레드에 안전하지 않습니다. 여러 스레드에서 동시에 접근할 경우 ConcurrentHashMap을 사용하는 것이 좋습니다.

import java.util.HashMap;

public class Main {
    public static void main(String[] args) {
        HashMap<String, Integer> map = new HashMap<>();
        
        // 데이터 추가
        map.put("apple", 1);
        map.put("banana", 2);
        map.put("orange", 3);

        // 데이터 조회
        System.out.println("apple의 값: " + map.get("apple"));  // 결과: apple의 값: 1

        // 데이터 삭제
        map.remove("banana");

        // 키가 존재하는지 확인
        System.out.println("banana가 존재하나요? " + map.containsKey("banana"));  // 결과: false
    }
}

좀 더 쉽게

HashMap은 사전처럼 작동하는 자료구조입니다. 마치 영어 사전에서 단어(키)를 입력하면 해당 단어의 뜻(값)을 찾을 수 있는 것처럼, HashMap도 키-값 쌍으로 데이터를 저장하고, 키를 사용해 값을 빠르게 찾을 수 있습니다.

HashMap의 기본 개념
키와 값(Key-Value): HashMap에 저장된 각각의 항목은 키와 값으로 이루어져 있어요.

예를 들어, "apple"이라는 키와 1이라는 값을 저장한다고 하면, HashMap에선 ("apple", 1) 이런 식으로 저장됩니다.
map.get("apple")을 호출하면 1이라는 값을 쉽게 찾을 수 있습니다.
고유한 키: 각 키는 고유해야 해요. 같은 키를 두 번 저장하려고 하면, 이전 값이 새 값으로 바뀝니다. 예를 들어, "apple" 키에 1을 저장한 후 다시 "apple"에 2를 저장하면, 최종적으로 "apple"의 값은 2가 됩니다.

빠른 검색과 추가: HashMap은 내부적으로 해시 함수를 사용해 키의 위치를 빠르게 찾아갑니다. 덕분에 데이터를 찾거나 추가하는 작업이 매우 빠릅니다.

import java.util.HashMap;

public class Main {
    public static void main(String[] args) {
        // 학생의 이름과 점수를 저장하는 HashMap
        HashMap<String, Integer> scores = new HashMap<>();
        
        // 데이터 추가
        scores.put("철수", 85);
        scores.put("영희", 92);
        scores.put("민수", 76);

        // 철수의 점수를 찾기
        System.out.println("철수의 점수: " + scores.get("철수"));  // 결과: 철수의 점수: 85

        // 민수의 점수를 변경하기
        scores.put("민수", 80);
        System.out.println("민수의 새로운 점수: " + scores.get("민수"));  // 결과: 민수의 새로운 점수: 80

        // 특정 학생이 있는지 확인하기
        System.out.println("영희가 있나요? " + scores.containsKey("영희"));  // 결과: 영희가 있나요? true

        // 학생의 점수 목록을 출력하기
        for (String key : scores.keySet()) {
            System.out.println(key + "의 점수: " + scores.get(key));
        }
    }
}

데이터 추가: scores.put("철수", 85);를 호출하면, "철수"라는 이름을 키로 하고 85를 값으로 하여 HashMap에 저장합니다.
데이터 조회: scores.get("철수");를 사용하면 "철수"라는 키로 저장된 값, 즉 85를 얻을 수 있습니다.
데이터 수정: scores.put("민수", 80);을 통해 "민수"의 점수를 80으로 수정할 수 있습니다.
키 존재 여부 확인: scores.containsKey("영희");를 통해 "영희"라는 이름이 HashMap에 있는지 확인할 수 있습니다.
이렇게 HashMap을 사용하면 빠르게 데이터를 추가하고 찾을 수 있습니다. 그래서 HashMap은 데이터를 많이 다루면서 빠른 검색이 필요할 때 매우 유용합니다.

0개의 댓글