관리 메뉴

거니의 velog

231122_SPRING 2 (1-1) 본문

대덕인재개발원_웹기반 애플리케이션

231122_SPRING 2 (1-1)

Unlimited00 2023. 11. 22. 08:34

[IMainService.java]

package kr.or.ddit.main.service;

import java.util.List;
import java.util.Map;

import kr.or.ddit.vo.BoardVO;

public interface IMainService {

	public List<BoardVO> selectBoardList();
	public Map<String, String> selectAllCount();
	
}

[MainServiceImpl.java]

package kr.or.ddit.main.service;

import java.util.List;
import java.util.Map;

import javax.inject.Inject;

import org.springframework.stereotype.Service;

import kr.or.ddit.main.dao.IMainDAO;
import kr.or.ddit.vo.BoardVO;

@Service
public class MainServiceImpl implements IMainService {

	@Inject
	private IMainDAO mainDao;
	
	@Override
	public List<BoardVO> selectBoardList() {
		return mainDao.selectBoardList();
	}

	@Override
	public Map<String, String> selectAllCount() {
		return mainDao.selectAllCount();
	}

}

[IMainDAO.java]

package kr.or.ddit.main.dao;

import java.util.List;
import java.util.Map;

import kr.or.ddit.vo.BoardVO;

public interface IMainDAO {

	public List<BoardVO> selectBoardList();
	public Map<String, String> selectAllCount();
	
}

[MainDAOImpl.java]

package kr.or.ddit.main.dao;

import java.util.List;
import java.util.Map;

import javax.inject.Inject;

import org.mybatis.spring.SqlSessionTemplate;
import org.springframework.stereotype.Repository;

import kr.or.ddit.vo.BoardVO;

@Repository
public class MainDAOImpl implements IMainDAO {

	@Inject
	private SqlSessionTemplate sqlSession;
	
	@Override
	public List<BoardVO> selectBoardList() {
		return sqlSession.selectList("Main.selectBoardList");
	}

	@Override
	public Map<String, String> selectAllCount() {
		return sqlSession.selectOne("Main.selectAllCount");
	}

}

[main_SQL.xml]

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

	<!--  
		정상적으로 동작하는 듯해 보이나 정상적으로 데이터가 출력되지 않음
		select * from board 
		where rownum <= 5 
		order by bono desc
	-->
	<select id="selectBoardList" resultType="boardVO">
		select b.* 
		from (
			select a.*, row_number() over (order by a.bono desc) rnum
			from (
				select 
					bono, botitle, bocontent, bowriter, bodate, bohit 
				from board 
				where 1=1 
				order by bono desc
			) a 
		) b 
		<![CDATA[
			where rnum <= 5
		]]>
	</select>
	
	<select id="selectAllCount" resultType="hashMap">
		select 
			(select count(bono) from board) boardCnt, 
			(select count(notice_no) from notice) noticeCnt, 
			(select count(free_no) from free) freeCnt
		from dual
	</select>

</mapper>

[MainController.java]

package kr.or.ddit.main.web;

import java.util.List;
import java.util.Map;

import javax.inject.Inject;

import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

import kr.or.ddit.main.service.IMainService;
import kr.or.ddit.vo.BoardVO;

@Controller
public class MainController {
	
	@Inject
	private IMainService mainService;

	@RequestMapping(value = { "/", "/main.do" }, method = RequestMethod.GET)
	public String main(Model model) {
		
		// 일반게시판 최신글 5개 목록 가져오기
		List<BoardVO> boardList = mainService.selectBoardList();
		// 공지사항 게시판, 자유 게시판 최신글 5개 목록 가져오기
		
		// 일반게시판, 공지사항게시판, 자유게시판 총 게시글 수
		Map<String, String> allCount = mainService.selectAllCount();
		
		model.addAttribute("boardList", boardList);
		model.addAttribute("allCount", allCount);
		
		return "main";
		
	}
	
}

[main.jsp]

<%@ page contentType="text/html; charset=utf-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<%@ page import="java.util.*"%>
<html>

<head>
    <link href="${pageContext.request.contextPath }/resources/css/bootstrap.min.css" rel="stylesheet">
    <link rel="stylesheet" href="${pageContext.request.contextPath }/resources/css/headers.css">
    <title>메인화면</title>
</head>
<style>
    .bi {
        vertical-align: -.125em;
        fill: currentColor;
    }
</style>

<body>
    <svg xmlns="http://www.w3.org/2000/svg" style="display: none;">
        <symbol id="bootstrap" viewBox="0 0 118 94">
            <title>Bootstrap</title>
            <path fill-rule="evenodd" clip-rule="evenodd" d="M24.509 0c-6.733 0-11.715 5.893-11.492 12.284.214 6.14-.064 14.092-2.066 20.577C8.943 39.365 5.547 43.485 0 44.014v5.972c5.547.529 8.943 4.649 10.951 11.153 2.002 6.485 2.28 14.437 2.066 20.577C12.794 88.106 17.776 94 24.51 94H93.5c6.733 0 11.714-5.893 11.491-12.284-.214-6.14.064-14.092 2.066-20.577 2.009-6.504 5.396-10.624 10.943-11.153v-5.972c-5.547-.529-8.934-4.649-10.943-11.153-2.002-6.484-2.28-14.437-2.066-20.577C105.214 5.894 100.233 0 93.5 0H24.508zM80 57.863C80 66.663 73.436 72 62.543 72H44a2 2 0 01-2-2V24a2 2 0 012-2h18.437c9.083 0 15.044 4.92 15.044 12.474 0 5.302-4.01 10.049-9.119 10.88v.277C75.317 46.394 80 51.21 80 57.863zM60.521 28.34H49.948v14.934h8.905c6.884 0 10.68-2.772 10.68-7.727 0-4.643-3.264-7.207-9.012-7.207zM49.948 49.2v16.458H60.91c7.167 0 10.964-2.876 10.964-8.281 0-5.406-3.903-8.178-11.425-8.178H49.948z"></path>
        </symbol>
        <symbol id="home" viewBox="0 0 16 16">
            <path d="M8.354 1.146a.5.5 0 0 0-.708 0l-6 6A.5.5 0 0 0 1.5 7.5v7a.5.5 0 0 0 .5.5h4.5a.5.5 0 0 0 .5-.5v-4h2v4a.5.5 0 0 0 .5.5H14a.5.5 0 0 0 .5-.5v-7a.5.5 0 0 0-.146-.354L13 5.793V2.5a.5.5 0 0 0-.5-.5h-1a.5.5 0 0 0-.5.5v1.293L8.354 1.146zM2.5 14V7.707l5.5-5.5 5.5 5.5V14H10v-4a.5.5 0 0 0-.5-.5h-3a.5.5 0 0 0-.5.5v4H2.5z" />
        </symbol>
        <symbol id="grid" viewBox="0 0 16 16">
            <path d="M1 2.5A1.5 1.5 0 0 1 2.5 1h3A1.5 1.5 0 0 1 7 2.5v3A1.5 1.5 0 0 1 5.5 7h-3A1.5 1.5 0 0 1 1 5.5v-3zM2.5 2a.5.5 0 0 0-.5.5v3a.5.5 0 0 0 .5.5h3a.5.5 0 0 0 .5-.5v-3a.5.5 0 0 0-.5-.5h-3zm6.5.5A1.5 1.5 0 0 1 10.5 1h3A1.5 1.5 0 0 1 15 2.5v3A1.5 1.5 0 0 1 13.5 7h-3A1.5 1.5 0 0 1 9 5.5v-3zm1.5-.5a.5.5 0 0 0-.5.5v3a.5.5 0 0 0 .5.5h3a.5.5 0 0 0 .5-.5v-3a.5.5 0 0 0-.5-.5h-3zM1 10.5A1.5 1.5 0 0 1 2.5 9h3A1.5 1.5 0 0 1 7 10.5v3A1.5 1.5 0 0 1 5.5 15h-3A1.5 1.5 0 0 1 1 13.5v-3zm1.5-.5a.5.5 0 0 0-.5.5v3a.5.5 0 0 0 .5.5h3a.5.5 0 0 0 .5-.5v-3a.5.5 0 0 0-.5-.5h-3zm6.5.5A1.5 1.5 0 0 1 10.5 9h3a1.5 1.5 0 0 1 1.5 1.5v3a1.5 1.5 0 0 1-1.5 1.5h-3A1.5 1.5 0 0 1 9 13.5v-3zm1.5-.5a.5.5 0 0 0-.5.5v3a.5.5 0 0 0 .5.5h3a.5.5 0 0 0 .5-.5v-3a.5.5 0 0 0-.5-.5h-3z" />
        </symbol>
    </svg>
    <main>
        <header>
            <div class="px-3 py-2 text-bg-dark">
                <div class="container">
                    <div class="d-flex flex-wrap align-items-center justify-content-center justify-content-lg-start">
                        <a href="/" class="d-flex align-items-center my-2 my-lg-0 me-lg-auto text-white text-decoration-none">
                            <svg class="bi me-2" width="40" height="32" role="img" aria-label="Bootstrap">
                                <use xlink:href="#bootstrap" />
                            </svg>
                        </a>
                        <ul class="nav col-12 col-lg-auto my-2 justify-content-center my-md-0 text-small">
                            <li>
                                <a href="/main.do" class="nav-link text-white">
                                    <svg class="bi d-block mx-auto mb-1" width="24" height="24">
                                        <use xlink:href="#home" />
                                    </svg> Home
                                </a>
                            </li>
                            <li>
                                <a href="/board/list.do" class="nav-link text-white">
                                    <svg class="bi d-block mx-auto mb-1" width="24" height="24">
                                        <use xlink:href="#grid" />
                                    </svg> 일반게시판
                                </a>
                            </li>
                            <li>
                                <a href="/notice/list.do" class="nav-link text-white">
                                    <svg class="bi d-block mx-auto mb-1" width="24" height="24">
                                        <use xlink:href="#grid" />
                                    </svg> 공지사항게시판
                                </a>
                            </li>
                            <li>
                                <a href="/free/list.do" class="nav-link text-white">
                                    <svg class="bi d-block mx-auto mb-1" width="24" height="24">
                                        <use xlink:href="#grid" />
                                    </svg> 자유게시판
                                </a>
                            </li>
                        </ul>
                    </div>
                </div>
            </div>
        </header>

        <div class="position-relative overflow-hidden p-3 p-md-8 m-md-8 text-center bg-white">
            <div class="col-md-8 p-lg-8 mx-auto my-5">
                <h1 class="display-4 fw-normal">게시판 작성 연습</h1>
                <p class="lead fw-normal">Spring framework를 이용한 게시판 CRUD Example</p>
            </div>
            <div class="product-device shadow-sm d-none d-md-block"></div>
            <div class="product-device product-device-2 shadow-sm d-none d-md-block"></div>
        </div>

        <div class="container">
            <div class="row">
                <div class="col-md-6">
                    <div align="left">
                        <h5>일반 게시판</h5>
                    </div>
                    <div align="right">
                        <span class="badge bg-dark-subtle border border-dark-subtle text-dark-emphasis rounded-pill">전체 ${allCount.BOARDCNT }건</span>
                    </div>
                    <form action="" method="post">
                        <div style="padding-top: 50px">
                            <table class="table">
                                <tr class="table-dark">
                                    <th>번호</th>
                                    <th>제목</th>
                                    <th>작성일</th>
                                </tr>
                                <c:choose>
                                	<c:when test="${empty boardList }">
		                                <tr>
		                                    <td colspan="3">조회하신 게시글이 존재하지 않습니다.</td>
		                                </tr>
                                	</c:when>
                                	<c:otherwise>
                                		<c:forEach items="${boardList }" var="board">
			                                <tr>
			                                    <td>${board.boNo }</td>
			                                    <td>
			                                    	<a href="/board/detail.do?boNo=${board.boNo }">${board.boTitle }</a>
			                                    </td>
			                                    <td>${board.boDate }</td>
			                                </tr>
                                		</c:forEach>
                                	</c:otherwise>
                                </c:choose>
                            </table>
                        </div>
                    </form>
                    <a href="/board/list.do" class="btn btn-outline-primary">&laquo;더보기</a>
                </div>
                <div class="col-md-6">
                    <div align="left">
                        <h5>공지사항</h5>
                    </div>
                    <div align="right">
                        <span class="badge bg-dark-subtle border border-dark-subtle text-dark-emphasis rounded-pill">전체 ${allCount.NOTICECNT }건</span>
                    </div>
                    <form action="" method="post">
                        <div style="padding-top: 50px">
                            <table class="table">
                                <tr class="table-dark">
                                    <th>번호</th>
                                    <th>제목</th>
                                    <th>작성일</th>
                                </tr>
                                <c:choose>
                                	<c:when test="${empty noticeList }">
		                                <tr>
		                                    <td colspan="3">조회하신 게시글이 존재하지 않습니다.</td>
		                                </tr>
                                	</c:when>
                                	<c:otherwise>
                                		<c:forEach items="${noticeList }" var="notice">
			                                <tr>
			                                    <td>${notice.noticeNo }</td>
			                                    <td>
			                                    	<a href="/notice/detail.do?noticeNo=${notice.noticeNo }">${notice.noticeTitle }</a>
			                                    </td>
			                                    <td>${notice.noticeDate }</td>
			                                </tr>
                                		</c:forEach>
                                	</c:otherwise>
                                </c:choose>
                            </table>
                        </div>
                    </form>
                    <a href="/notice/list.do" class="btn btn-outline-primary">&laquo;더보기</a>
                </div>
            </div>
            <br />
            <div class="row">
                <div class="col-md-6">
                    <div align="left">
                        <h5>자유 게시판</h5>
                    </div>
                    <div align="right">
                        <span class="badge bg-dark-subtle border border-dark-subtle text-dark-emphasis rounded-pill">전체 ${allCount.FREECNT }건</span>
                    </div>
                    <form action="" method="post">
                        <div style="padding-top: 50px">
                            <table class="table">
                                <tr class="table-dark">
                                    <th>번호</th>
                                    <th>제목</th>
                                    <th>작성일</th>
                                </tr>
                                <c:choose>
                                	<c:when test="${empty freeList }">
		                                <tr>
		                                    <td colspan="3">조회하신 게시글이 존재하지 않습니다.</td>
		                                </tr>
                                	</c:when>
                                	<c:otherwise>
                                		<c:forEach items="${freeList }" var="free">
			                                <tr>
			                                    <td>${free.freeNo }</td>
			                                    <td>
			                                    	<a href="/free/detail.do?freeNo=${free.freeNo }">${free.freeTitle }</a>
			                                    </td>
			                                    <td>${free.freeDate }</td>
			                                </tr>
                                		</c:forEach>
                                	</c:otherwise>
                                </c:choose>
                            </table>
                        </div>
                    </form>
                    <a href="/free/list.do" class="btn btn-outline-primary">&laquo;더보기</a>
                </div>
                <div class="col-md-6"></div>
            </div>
            <br />
        </div>
    </main>
</body>

</html>

- http://localhost/main.do


[IMainService.java]

package kr.or.ddit.main.service;

import java.util.List;
import java.util.Map;

import kr.or.ddit.vo.BoardVO;
import kr.or.ddit.vo.FreeVO;
import kr.or.ddit.vo.NoticeVO;

public interface IMainService {

	public List<BoardVO> selectBoardList();
	public Map<String, String> selectAllCount();
	public List<NoticeVO> selectNoticeList();
	public List<FreeVO> selectFreeList();
	
}

[MainServiceImpl.java]

package kr.or.ddit.main.service;

import java.util.List;
import java.util.Map;

import javax.inject.Inject;

import org.springframework.stereotype.Service;

import kr.or.ddit.main.dao.IMainDAO;
import kr.or.ddit.vo.BoardVO;
import kr.or.ddit.vo.FreeVO;
import kr.or.ddit.vo.NoticeVO;

@Service
public class MainServiceImpl implements IMainService {

	@Inject
	private IMainDAO mainDao;
	
	@Override
	public List<BoardVO> selectBoardList() {
		return mainDao.selectBoardList();
	}

	@Override
	public Map<String, String> selectAllCount() {
		return mainDao.selectAllCount();
	}
	
	@Override
	public List<NoticeVO> selectNoticeList() {
		return mainDao.selectNoticeList();
	}
	
	@Override
	public List<FreeVO> selectFreeList() {
		return mainDao.selectFreeList();
	}

}

[IMainDAO.java]

package kr.or.ddit.main.dao;

import java.util.List;
import java.util.Map;

import kr.or.ddit.vo.BoardVO;
import kr.or.ddit.vo.FreeVO;
import kr.or.ddit.vo.NoticeVO;

public interface IMainDAO {

	public List<BoardVO> selectBoardList();
	public Map<String, String> selectAllCount();
	public List<NoticeVO> selectNoticeList();
	public List<FreeVO> selectFreeList();
	
}

[MainDAOImpl.java]

package kr.or.ddit.main.dao;

import java.util.List;
import java.util.Map;

import javax.inject.Inject;

import org.mybatis.spring.SqlSessionTemplate;
import org.springframework.stereotype.Repository;

import kr.or.ddit.vo.BoardVO;
import kr.or.ddit.vo.FreeVO;
import kr.or.ddit.vo.NoticeVO;

@Repository
public class MainDAOImpl implements IMainDAO {

	@Inject
	private SqlSessionTemplate sqlSession;
	
	@Override
	public List<BoardVO> selectBoardList() {
		return sqlSession.selectList("Main.selectBoardList");
	}

	@Override
	public Map<String, String> selectAllCount() {
		return sqlSession.selectOne("Main.selectAllCount");
	}
	
	@Override
	public List<NoticeVO> selectNoticeList() {
		return sqlSession.selectList("Main.selectNoticeList");
	}
	
	@Override
	public List<FreeVO> selectFreeList() {
		return sqlSession.selectList("Main.selectFreeList");
	}

}

[main_SQL.xml]

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

	<!--  
		정상적으로 동작하는 듯해 보이나 정상적으로 데이터가 출력되지 않음
		select * from board 
		where rownum <= 5 
		order by bono desc
	-->
	<select id="selectBoardList" resultType="boardVO">
		select b.* 
		from (
			select a.*, row_number() over (order by a.bono desc) rnum
			from (
				select 
					bono, botitle, bocontent, bowriter, bodate, bohit 
				from board 
				where 1=1 
				order by bono desc
			) a 
		) b 
		<![CDATA[
			where rnum <= 5
		]]>
	</select>
	
	<select id="selectAllCount" resultType="hashMap">
		select 
			(select count(bono) from board) boardCnt, 
			(select count(notice_no) from notice) noticeCnt, 
			(select count(free_no) from free) freeCnt
		from dual
	</select>
	
	<select id="selectNoticeList" resultType="noticeVO">
		select b.* 
		from (
			select a.*, row_number() over (order by a.notice_no desc) rnum
			from (
				select 
					notice_no, notice_title, notice_content, notice_writer, notice_date, notice_hit 
				from notice 
				where 1=1 
				order by notice_no desc
			) a 
		) b 
		<![CDATA[
			where rnum <= 5
		]]>
	</select>
	
	<select id="selectFreeList" resultType="freeVO">
		select b.* 
		from (
			select a.*, row_number() over (order by a.free_no desc) rnum
			from (
				select 
					free_no, free_title, free_content, free_writer, free_date, free_hit 
				from free 
				where 1=1 
				order by free_no desc
			) a 
		) b 
		<![CDATA[
			where rnum <= 5
		]]>
	</select>

</mapper>

[main.jsp]

<%@ page contentType="text/html; charset=utf-8"%>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<%@ page import="java.util.*"%>
<html>

<head>
    <link href="${pageContext.request.contextPath }/resources/css/bootstrap.min.css" rel="stylesheet">
    <link rel="stylesheet" href="${pageContext.request.contextPath }/resources/css/headers.css">
    <title>메인화면</title>
</head>
<style>
    .bi {
        vertical-align: -.125em;
        fill: currentColor;
    }
</style>

<body>
    <svg xmlns="http://www.w3.org/2000/svg" style="display: none;">
        <symbol id="bootstrap" viewBox="0 0 118 94">
            <title>Bootstrap</title>
            <path fill-rule="evenodd" clip-rule="evenodd" d="M24.509 0c-6.733 0-11.715 5.893-11.492 12.284.214 6.14-.064 14.092-2.066 20.577C8.943 39.365 5.547 43.485 0 44.014v5.972c5.547.529 8.943 4.649 10.951 11.153 2.002 6.485 2.28 14.437 2.066 20.577C12.794 88.106 17.776 94 24.51 94H93.5c6.733 0 11.714-5.893 11.491-12.284-.214-6.14.064-14.092 2.066-20.577 2.009-6.504 5.396-10.624 10.943-11.153v-5.972c-5.547-.529-8.934-4.649-10.943-11.153-2.002-6.484-2.28-14.437-2.066-20.577C105.214 5.894 100.233 0 93.5 0H24.508zM80 57.863C80 66.663 73.436 72 62.543 72H44a2 2 0 01-2-2V24a2 2 0 012-2h18.437c9.083 0 15.044 4.92 15.044 12.474 0 5.302-4.01 10.049-9.119 10.88v.277C75.317 46.394 80 51.21 80 57.863zM60.521 28.34H49.948v14.934h8.905c6.884 0 10.68-2.772 10.68-7.727 0-4.643-3.264-7.207-9.012-7.207zM49.948 49.2v16.458H60.91c7.167 0 10.964-2.876 10.964-8.281 0-5.406-3.903-8.178-11.425-8.178H49.948z"></path>
        </symbol>
        <symbol id="home" viewBox="0 0 16 16">
            <path d="M8.354 1.146a.5.5 0 0 0-.708 0l-6 6A.5.5 0 0 0 1.5 7.5v7a.5.5 0 0 0 .5.5h4.5a.5.5 0 0 0 .5-.5v-4h2v4a.5.5 0 0 0 .5.5H14a.5.5 0 0 0 .5-.5v-7a.5.5 0 0 0-.146-.354L13 5.793V2.5a.5.5 0 0 0-.5-.5h-1a.5.5 0 0 0-.5.5v1.293L8.354 1.146zM2.5 14V7.707l5.5-5.5 5.5 5.5V14H10v-4a.5.5 0 0 0-.5-.5h-3a.5.5 0 0 0-.5.5v4H2.5z" />
        </symbol>
        <symbol id="grid" viewBox="0 0 16 16">
            <path d="M1 2.5A1.5 1.5 0 0 1 2.5 1h3A1.5 1.5 0 0 1 7 2.5v3A1.5 1.5 0 0 1 5.5 7h-3A1.5 1.5 0 0 1 1 5.5v-3zM2.5 2a.5.5 0 0 0-.5.5v3a.5.5 0 0 0 .5.5h3a.5.5 0 0 0 .5-.5v-3a.5.5 0 0 0-.5-.5h-3zm6.5.5A1.5 1.5 0 0 1 10.5 1h3A1.5 1.5 0 0 1 15 2.5v3A1.5 1.5 0 0 1 13.5 7h-3A1.5 1.5 0 0 1 9 5.5v-3zm1.5-.5a.5.5 0 0 0-.5.5v3a.5.5 0 0 0 .5.5h3a.5.5 0 0 0 .5-.5v-3a.5.5 0 0 0-.5-.5h-3zM1 10.5A1.5 1.5 0 0 1 2.5 9h3A1.5 1.5 0 0 1 7 10.5v3A1.5 1.5 0 0 1 5.5 15h-3A1.5 1.5 0 0 1 1 13.5v-3zm1.5-.5a.5.5 0 0 0-.5.5v3a.5.5 0 0 0 .5.5h3a.5.5 0 0 0 .5-.5v-3a.5.5 0 0 0-.5-.5h-3zm6.5.5A1.5 1.5 0 0 1 10.5 9h3a1.5 1.5 0 0 1 1.5 1.5v3a1.5 1.5 0 0 1-1.5 1.5h-3A1.5 1.5 0 0 1 9 13.5v-3zm1.5-.5a.5.5 0 0 0-.5.5v3a.5.5 0 0 0 .5.5h3a.5.5 0 0 0 .5-.5v-3a.5.5 0 0 0-.5-.5h-3z" />
        </symbol>
    </svg>
    <main>
        <header>
            <div class="px-3 py-2 text-bg-dark">
                <div class="container">
                    <div class="d-flex flex-wrap align-items-center justify-content-center justify-content-lg-start">
                        <a href="/" class="d-flex align-items-center my-2 my-lg-0 me-lg-auto text-white text-decoration-none">
                            <svg class="bi me-2" width="40" height="32" role="img" aria-label="Bootstrap">
                                <use xlink:href="#bootstrap" />
                            </svg>
                        </a>
                        <ul class="nav col-12 col-lg-auto my-2 justify-content-center my-md-0 text-small">
                            <li>
                                <a href="/main.do" class="nav-link text-white">
                                    <svg class="bi d-block mx-auto mb-1" width="24" height="24">
                                        <use xlink:href="#home" />
                                    </svg> Home
                                </a>
                            </li>
                            <li>
                                <a href="/board/list.do" class="nav-link text-white">
                                    <svg class="bi d-block mx-auto mb-1" width="24" height="24">
                                        <use xlink:href="#grid" />
                                    </svg> 일반게시판
                                </a>
                            </li>
                            <li>
                                <a href="/notice/list.do" class="nav-link text-white">
                                    <svg class="bi d-block mx-auto mb-1" width="24" height="24">
                                        <use xlink:href="#grid" />
                                    </svg> 공지사항게시판
                                </a>
                            </li>
                            <li>
                                <a href="/free/list.do" class="nav-link text-white">
                                    <svg class="bi d-block mx-auto mb-1" width="24" height="24">
                                        <use xlink:href="#grid" />
                                    </svg> 자유게시판
                                </a>
                            </li>
                        </ul>
                    </div>
                </div>
            </div>
        </header>

        <div class="position-relative overflow-hidden p-3 p-md-8 m-md-8 text-center bg-white">
            <div class="col-md-8 p-lg-8 mx-auto my-5">
                <h1 class="display-4 fw-normal">게시판 작성 연습</h1>
                <p class="lead fw-normal">Spring framework를 이용한 게시판 CRUD Example</p>
            </div>
            <div class="product-device shadow-sm d-none d-md-block"></div>
            <div class="product-device product-device-2 shadow-sm d-none d-md-block"></div>
        </div>

        <div class="container">
            <div class="row">
                <div class="col-md-6">
                    <div align="left">
                        <h5>일반 게시판</h5>
                    </div>
                    <div align="right">
                        <span class="badge bg-dark-subtle border border-dark-subtle text-dark-emphasis rounded-pill">전체 ${allCount.BOARDCNT }건</span>
                    </div>
                    <form action="" method="post">
                        <div style="padding-top: 50px">
                            <table class="table">
                                <tr class="table-dark">
                                    <th>번호</th>
                                    <th>제목</th>
                                    <th>작성일</th>
                                </tr>
                                <c:choose>
                                	<c:when test="${empty boardList }">
		                                <tr>
		                                    <td colspan="3">조회하신 게시글이 존재하지 않습니다.</td>
		                                </tr>
                                	</c:when>
                                	<c:otherwise>
                                		<c:forEach items="${boardList }" var="board">
			                                <tr>
			                                    <td>${board.boNo }</td>
			                                    <td>
			                                    	<a href="/board/detail.do?boNo=${board.boNo }">${board.boTitle }</a>
			                                    </td>
			                                    <td>${board.boDate }</td>
			                                </tr>
                                		</c:forEach>
                                	</c:otherwise>
                                </c:choose>
                            </table>
                        </div>
                    </form>
                    <a href="/board/list.do" class="btn btn-outline-primary">&laquo;더보기</a>
                </div>
                <div class="col-md-6">
                    <div align="left">
                        <h5>공지사항</h5>
                    </div>
                    <div align="right">
                        <span class="badge bg-dark-subtle border border-dark-subtle text-dark-emphasis rounded-pill">전체 ${allCount.NOTICECNT }건</span>
                    </div>
                    <form action="" method="post">
                        <div style="padding-top: 50px">
                            <table class="table">
                                <tr class="table-dark">
                                    <th>번호</th>
                                    <th>제목</th>
                                    <th>작성일</th>
                                </tr>
                                <c:choose>
                                	<c:when test="${empty noticeList }">
		                                <tr>
		                                    <td colspan="3">조회하신 게시글이 존재하지 않습니다.</td>
		                                </tr>
                                	</c:when>
                                	<c:otherwise>
                                		<c:forEach items="${noticeList }" var="notice">
			                                <tr>
			                                    <td>${notice.noticeNo }</td>
			                                    <td>
			                                    	<a href="/notice/detail.do?noticeNo=${notice.noticeNo }">${notice.noticeTitle }</a>
			                                    </td>
			                                    <td>${notice.noticeDate }</td>
			                                </tr>
                                		</c:forEach>
                                	</c:otherwise>
                                </c:choose>
                            </table>
                        </div>
                    </form>
                    <a href="/notice/list.do" class="btn btn-outline-primary">&laquo;더보기</a>
                </div>
            </div>
            <br />
            <div class="row">
                <div class="col-md-6">
                    <div align="left">
                        <h5>자유 게시판</h5>
                    </div>
                    <div align="right">
                        <span class="badge bg-dark-subtle border border-dark-subtle text-dark-emphasis rounded-pill">전체 ${allCount.FREECNT }건</span>
                    </div>
                    <form action="" method="post">
                        <div style="padding-top: 50px">
                            <table class="table">
                                <tr class="table-dark">
                                    <th>번호</th>
                                    <th>제목</th>
                                    <th>작성일</th>
                                </tr>
                                <c:choose>
                                	<c:when test="${empty freeList }">
		                                <tr>
		                                    <td colspan="3">조회하신 게시글이 존재하지 않습니다.</td>
		                                </tr>
                                	</c:when>
                                	<c:otherwise>
                                		<c:forEach items="${freeList }" var="free">
			                                <tr>
			                                    <td>${free.freeNo }</td>
			                                    <td>
			                                    	<a href="/free/detail.do?freeNo=${free.freeNo }">${free.freeTitle }</a>
			                                    </td>
			                                    <td>${free.freeDate }</td>
			                                </tr>
                                		</c:forEach>
                                	</c:otherwise>
                                </c:choose>
                            </table>
                        </div>
                    </form>
                    <a href="/free/list.do" class="btn btn-outline-primary">&laquo;더보기</a>
                </div>
                <div class="col-md-6"></div>
            </div>
            <br />
        </div>
    </main>
</body>

</html>

- http://localhost/


https://www.egovframe.go.kr/home/sub.do?menuNo=4

 

실행환경 - Release Notes | 표준프레임워크 포털 eGovFrame

처리중입니다. 잠시만 기다려주십시오.

www.egovframe.go.kr


* 기본 설정 죽 해 나가기~

https://bbbb7788.tistory.com/220

 

231026_JSP 개론 1

1. 처음 - 회사에서 우리에게 원하는 건 기본적인 CRUD [ JSP, 스프링1, 스프링2 ] (1) 수업은 JSP, 스프링1, 스프링2의 순서대로 진행한다. - Product, Book 쇼핑몰을 만들어 보면서 JSP를 공부한다. - Book 게

bbbb7788.tistory.com

https://bbbb7788.tistory.com/299

 

231115_SPRING 1 (1)

* 서블릿을 만들지 않고 컨트롤러로 컨트롤 한다. [HomeController.java] package kr.or.ddit; import java.text.DateFormat; import java.util.Date; import java.util.Locale; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.spr

bbbb7788.tistory.com

[pom.xml] - 서블릿 버전을 3.1.0로 수정

		<!-- Servlet -->
		<dependency>
			<groupId>javax.servlet</groupId>
			<artifactId>javax.servlet-api</artifactId>
			<version>3.1.0</version>
			<scope>provided</scope>
		</dependency>
		<dependency>
			<groupId>javax.servlet.jsp</groupId>
			<artifactId>jsp-api</artifactId>
			<version>2.1</version>
			<scope>provided</scope>
		</dependency>
		<dependency>
			<groupId>javax.servlet</groupId>
			<artifactId>jstl</artifactId>
			<version>1.2</version>
		</dependency>

[web.xml]

<?xml version="1.0" encoding="UTF-8"?>
<web-app version="3.1" xmlns="http://java.sun.com/xml/ns/javaee"
	xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://java.sun.com/xml/ns/javaee https://java.sun.com/xml/ns/javaee/web-app_3_1.xsd">

	<!-- The definition of the Root Spring Container shared by all Servlets and Filters -->
	<context-param>
		<param-name>contextConfigLocation</param-name>
		<param-value>/WEB-INF/spring/root-context.xml</param-value>
	</context-param>
	
	<!-- Creates the Spring Container shared by all Servlets and Filters -->
	<listener>
		<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
	</listener>

	<!-- Processes application requests -->
	<servlet>
		<servlet-name>appServlet</servlet-name>
		<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
		<init-param>
			<param-name>contextConfigLocation</param-name>
			<param-value>/WEB-INF/spring/appServlet/servlet-context.xml</param-value>
		</init-param>
		<load-on-startup>1</load-on-startup>
	</servlet>
		
	<servlet-mapping>
		<servlet-name>appServlet</servlet-name>
		<url-pattern>/</url-pattern>
	</servlet-mapping>
	
	<!--  
		한글 처리를 위한 UTF-8 필터 등록
		JSP나 서블릿 처리할 때마다 넘겨받은 request를 setCharacterEncoding으로 UTF-8 설정했던 부분을 필터로 대체함
	-->
	<filter>
		<filter-name>encordingFilter</filter-name>
		<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
		<init-param>
			<param-name>encoding</param-name>
			<param-value>UTF-8</param-value>
		</init-param>
		<init-param>
			<param-name>forceEncoding</param-name>
			<param-value>true</param-value>
		</init-param>
	</filter>
	<filter-mapping>
		<filter-name>encordingFilter</filter-name>
		<url-pattern>/*</url-pattern>
	</filter-mapping>

</web-app>

[home.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8" 
    session="false"%>
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<!DOCTYPE html>
<html>

    <head>
        <title>Home</title>
    </head>

    <body>
        <h1>
            Hello world!
        </h1>

        <p> The time on the server is ${serverTime}. </p>
    </body>

</html>

- http://localhost/


[앞으로 배울 것들]

* 웹에서 클라이언트와 서버가 데이터를 주고 받는 과정이 중요. 스프링 1에서는 이 두 녀석을 이용해 CRUD를 간단히 맛봄. 

* 클라이언트에서 서버로 넘긴 요청을 받는 방법에 대해 여러 개 알아보고,
  보낸 요청을 서버가 받고 데이터를 꺼내는 방법에 대해 여러개 알아 볼 것이다.

* 서버에서 클라이언트로 응답을 내보내는 방법도 여러개 알아본다.
   이를 동기, 비동기로 해보고, + 파일 업로드/다운로드 + 필터 + 인터셉터 + AOP + 트랜잭션 + 시큐리티 + DB 연동

* 여기에서 설정들이 각각 존재한다. 이제 우리가 알아야 할 것은 이 설정도 같이 알아나가야 한다.


┌───────────────────────────────────────
│	실전 스프링 웹 개발
│	:: 2023-11-22
└───────────────────────────────────────

	[ 1장 : 스프링 개발 환경 ]
	
	# 개발환경
	
	Tool : Spring Tool Suite(STS) 3.9.15(eclipse 4.16)
	Java : JDK 1.8
	Orecle : Oracle 11g XE
	Server : Apache Tomcat 8.5.x
	Mybatis : 3.5.x
	SpringFrameWork : 5.3.25
	
		** egovframework(전자정부 프레임워크)와 비교했을 떄, 현재 버전이 실행환경 4.1.0에서 사용하는 버전과 차이가 없다.
		** 많은 STS 버전들 중, 3.9.15 버전이 plugin을 설치하거나 설정을 진행할 때에 에러 발생 확률이 적었음.
		
	[ 2장 : 프로젝트 생성 ]
	
	# 실전 스프링 웹 개발 준비
	
	1. STS 설치 후 실행
	2. STS 설정
		- window > preferences
		- 인코딩(UTF-8) 및 폰트 설정
		- Java 설정
			> Installed JREs > JDK 1.8 설정
		- Server 설정
			> Runtime Environment > Apache-Tomcat 설정
	3. 스프링 프로젝트 만들기
		- Spring legacy project 생성
			> 프로젝트 명 : Spring2Project
			> 패키지 : kr.or.ddit (프로젝트 base package)
			> template : Spring MVC Project
			
		# MVC 프로젝트 구성 확인
		- pom.xml													: 메이븐 프로젝트 빌드 파일
		- src/main/java												: 자바 소스 경로
		- src/main/resources										: 리소스 파일 경로
		- src/.../WEB-INF/web.xml									: 웹 컨테이너 설정 파일
		- src/.../WEB-INF/spring/root-context.xml					: 스프링 설정 파일
		- src/.../WEB-INF/spring/appServlet/servlet-context.xml		: 스프링 웹 설정 파일
		- src/.../WEB-INF/views										: 뷰 파일 경로
	4. 웹 서버 설정
		- overview : timeout 120s / port 80 설정
		- module : path '/' 설정
	5. 프로젝트 환경 설정
		- Deployment Assembly : Maven Dependency 확인
		- Java Build Path : [3대장 확인] JDK, Server, Maven
		- Java Compiler : compliance level 1.8 확인
		- Project Facets : Dynamic Web Module 3.1, Java 1.8 설정
	6. pom.xml 설정
		- java-version : 1.8
		- org.springframework-version : 5.3.25
		- javax.servlet : 3.1.0
		- plugin source 1.8 / plugin target 1.8
		
			# Maven 적용
			- 프로젝트 우클릭 > Run As > Maven Clean
									> Maven Build(Goals: compile)
	7. 웹 컨테이너 설정(web.xml)
		- version : 3.1
		- schemaLocation : web-app_3_1
	8. 인코딩 필터 적용
		- 웹 컨테이너 설정(web.xml)
		- encodingFilter 설정
	9. 로그 레벨 설정(log4j.xml)
		- root level : debug
	10. 프로젝트 실행
		- HomeController, home.jsp
		- 'http://localhost/' 실행
		- home.jsp에서 page 디렉티브 내 pageEncoding, contentType 속성 추가 후 UTF-8 인코딩 설정
		
		** Hello World! 페이지를 한글 깨짐 없이 확인 할 수 있으면 STS 설정 및 Spring2Project 설정에 문제가 없음을 검증

[BoardController.java]

package kr.or.ddit.controller.board;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;

@Controller
@RequestMapping("/board")
public class BoardController {

	/*
	 * [ 3장 : 컨트롤러 요청 매핑 ]
	 * 
	 * 		1. 요청 경로 매핑
	 * 
	 * 			- @RequestMapping의 value 속성에 요청 경로를 설정한다.
	 * 			- 요청 경로는 반드시 설정해야 하는 필수 정보이다.
	 * 			- 속성이 하나일 때는 속성명을 생략할 수 있다. (default는 value)
	 * 			- 컨트롤러의 클래스 레벨과 메서드 레벨로 지정할 수 있다.
	 * 			- 클래스 레벨로 요청 경로를 지정하면 메서드 레벨에서 지정한 경로의 기본 경로로 취급된다.
	 * 			- 클래스 레벨의 요청 경로에 메서드 레벨의 요청 경로를 덧붙인 형태가 최종 경로가 된다.
	 */
	
	private static final Logger log = LoggerFactory.getLogger(BoardController.class);
	
	@RequestMapping(value = "/register")
	public void registerForm() {
		log.info("registerForm() 실행...!");
	}
	
}

- http://localhost/board/register


[register.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>BOARD</title>
	</head>
	<body>
		<h3>REGISTER</h3>
	</body>
</html>

- void로 설정해도 RequestMapping의 각각의 경로가 파일의 위치를 추론하여 파일을 내보내줌


package kr.or.ddit.controller.board;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;

@Controller
@RequestMapping("/board")
public class BoardController {

	/*
	 * [ 3장 : 컨트롤러 요청 매핑 ]
	 * 
	 * 		1. 요청 경로 매핑
	 * 
	 * 			- @RequestMapping의 value 속성에 요청 경로를 설정한다.
	 * 			- 요청 경로는 반드시 설정해야 하는 필수 정보이다.
	 * 			- 속성이 하나일 때는 속성명을 생략할 수 있다. (default는 value)
	 * 			- 컨트롤러의 클래스 레벨과 메서드 레벨로 지정할 수 있다.
	 * 			- 클래스 레벨로 요청 경로를 지정하면 메서드 레벨에서 지정한 경로의 기본 경로로 취급된다.
	 * 			- 클래스 레벨의 요청 경로에 메서드 레벨의 요청 경로를 덧붙인 형태가 최종 경로가 된다.
	 */
	
	private static final Logger log = LoggerFactory.getLogger(BoardController.class);
	
	@RequestMapping(value = "/register")
	public void registerForm() {
		log.info("registerForm() 실행...!");
	}
	
	@RequestMapping(value = "/modify")
	public void modifyForm() {
		log.info("modifyForm() 실행...!");
	}
	
	@RequestMapping(value = "/list")
	public void list() {
		log.info("list() 실행...!");
	}
	
}

[modify.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>BOARD</title>
	</head>
	<body>
		<h3>MODIFY</h3>
	</body>
</html>

[list.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>BOARD</title>
	</head>
	<body>
		<h3>LIST</h3>
	</body>
</html>

- http://localhost/board/modify

- http://localhost/board/list


package kr.or.ddit.controller.board;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;

@Controller
@RequestMapping("/board")
public class BoardController {

	/*
	 * [ 3장 : 컨트롤러 요청 매핑 ]
	 * 
	 * 		1. 요청 경로 매핑
	 * 
	 * 			- @RequestMapping의 value 속성에 요청 경로를 설정한다.
	 * 			- 요청 경로는 반드시 설정해야 하는 필수 정보이다.
	 * 			- 속성이 하나일 때는 속성명을 생략할 수 있다. (default는 value)
	 * 			- 컨트롤러의 클래스 레벨과 메서드 레벨로 지정할 수 있다.
	 * 			- 클래스 레벨로 요청 경로를 지정하면 메서드 레벨에서 지정한 경로의 기본 경로로 취급된다.
	 * 			- 클래스 레벨의 요청 경로에 메서드 레벨의 요청 경로를 덧붙인 형태가 최종 경로가 된다.
	 */
	
	private static final Logger log = LoggerFactory.getLogger(BoardController.class);
	
	@RequestMapping(value = "/register")
	public void registerForm() {
		log.info("registerForm() 실행...!");
	}
	
	@RequestMapping(value = "/modify")
	public void modifyForm() {
		log.info("modifyForm() 실행...!");
	}
	
	@RequestMapping(value = "/list")
	public void list() {
		log.info("list() 실행...!");
	}
	
	/*
	 * 		2. 경로 패턴 매핑
	 * 
	 * 			- 요청 경로를 동적으로 표현이 가능한 경로 패턴을 지정할 수 있다.
	 * 			- URL 경로 상의 변하는 값을 경로 변수로 취급한다.
	 * 			- 경로 변수에 해당하는 값을 파라미터 변수에 설정할 수 있다.
	 */
	
	@RequestMapping(value = "/read/{boardNo}")
	public String read(@PathVariable("boardNo") int boardNo) {
		log.info("read() 실행...!");
		log.info("경로 상의 포함된 boardNo : " + boardNo);
		return "board/read";
	}
	
}

- http://localhost/board/read/100


[read.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>BOARD</title>
	</head>
	<body>
		<h3>READ</h3>
	</body>
</html>

- http://localhost/board/read/200


package kr.or.ddit.controller.board;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

@Controller
@RequestMapping("/board")
public class BoardController {

	/*
	 * [ 3장 : 컨트롤러 요청 매핑 ]
	 * 
	 * 		1. 요청 경로 매핑
	 * 
	 * 			- @RequestMapping의 value 속성에 요청 경로를 설정한다.
	 * 			- 요청 경로는 반드시 설정해야 하는 필수 정보이다.
	 * 			- 속성이 하나일 때는 속성명을 생략할 수 있다. (default는 value)
	 * 			- 컨트롤러의 클래스 레벨과 메서드 레벨로 지정할 수 있다.
	 * 			- 클래스 레벨로 요청 경로를 지정하면 메서드 레벨에서 지정한 경로의 기본 경로로 취급된다.
	 * 			- 클래스 레벨의 요청 경로에 메서드 레벨의 요청 경로를 덧붙인 형태가 최종 경로가 된다.
	 */
	
	private static final Logger log = LoggerFactory.getLogger(BoardController.class);
	
	@RequestMapping(value = "/register")
	public void registerForm() {
		log.info("registerForm() 실행...!");
	}
	
	@RequestMapping(value = "/modify")
	public void modifyForm() {
		log.info("modifyForm() 실행...!");
	}
	
	@RequestMapping(value = "/list")
	public void list() {
		log.info("list() 실행...!");
	}
	
	/*
	 * 		2. 경로 패턴 매핑
	 * 
	 * 			- 요청 경로를 동적으로 표현이 가능한 경로 패턴을 지정할 수 있다.
	 * 			- URL 경로 상의 변하는 값을 경로 변수로 취급한다.
	 * 			- 경로 변수에 해당하는 값을 파라미터 변수에 설정할 수 있다.
	 */
	
	@RequestMapping(value = "/read/{boardNo}")
	public String read(@PathVariable("boardNo") int boardNo) {
		log.info("read() 실행...!");
		log.info("경로 상의 포함된 boardNo : " + boardNo);
		return "board/read";
	}
	
	/*
	 *		3. HTTP 메서드 매핑
	 *
	 *			- method 속성을 사용하여 HTTP 메서드를 매핑 조건으로 지정할 수 있다.
	 *			- 화면으로 응답하는 경우에는 HTTP 메서드로 GET방식과 POST방식 두 가지를 사용할 수 있다.
	 */
	
	// HTTP 메서드 매핑 실행 페이지
	
	@RequestMapping(value = "/formHome", method = RequestMethod.GET)
	public String formHome() {
		log.info("formHome() 실행...!");
		return "formHome";
	}
	
}

[formHome.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>FormHome</title>
	</head>
	<body>
	
		<form action="/board/http/register">
			<button type="submit">register(GET)</button>
		</form>
		<form action="/board/http/register" method="post">
			<button type="submit">register(POST)</button>
		</form>
		
		<form action="/board/http/modify">
			<button type="submit">modify(GET)</button>
		</form>
		<form action="/board/http/modify" method="post">
			<button type="submit">modify(POST)</button>
		</form>
		
		<form action="/board/http/remove" method="post">
			<button type="submit">remove(POST)</button>
		</form>
		
		<form action="/board/http/list">
			<button type="submit">list(GET)</button>
		</form>
		
	</body>
</html>

- http://localhost/board/formHome


package kr.or.ddit.controller.board;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

@Controller
@RequestMapping("/board")
public class BoardController {

	/*
	 * [ 3장 : 컨트롤러 요청 매핑 ]
	 * 
	 * 		1. 요청 경로 매핑
	 * 
	 * 			- @RequestMapping의 value 속성에 요청 경로를 설정한다.
	 * 			- 요청 경로는 반드시 설정해야 하는 필수 정보이다.
	 * 			- 속성이 하나일 때는 속성명을 생략할 수 있다. (default는 value)
	 * 			- 컨트롤러의 클래스 레벨과 메서드 레벨로 지정할 수 있다.
	 * 			- 클래스 레벨로 요청 경로를 지정하면 메서드 레벨에서 지정한 경로의 기본 경로로 취급된다.
	 * 			- 클래스 레벨의 요청 경로에 메서드 레벨의 요청 경로를 덧붙인 형태가 최종 경로가 된다.
	 */
	
	private static final Logger log = LoggerFactory.getLogger(BoardController.class);
	
	@RequestMapping(value = "/register")
	public void registerForm() {
		log.info("registerForm() 실행...!");
	}
	
	@RequestMapping(value = "/modify")
	public void modifyForm() {
		log.info("modifyForm() 실행...!");
	}
	
	@RequestMapping(value = "/list")
	public void list() {
		log.info("list() 실행...!");
	}
	
	/*
	 * 		2. 경로 패턴 매핑
	 * 
	 * 			- 요청 경로를 동적으로 표현이 가능한 경로 패턴을 지정할 수 있다.
	 * 			- URL 경로 상의 변하는 값을 경로 변수로 취급한다.
	 * 			- 경로 변수에 해당하는 값을 파라미터 변수에 설정할 수 있다.
	 */
	
	@RequestMapping(value = "/read/{boardNo}")
	public String read(@PathVariable("boardNo") int boardNo) {
		log.info("read() 실행...!");
		log.info("경로 상의 포함된 boardNo : " + boardNo);
		return "board/read";
	}
	
	/*
	 *		3. HTTP 메서드 매핑
	 *
	 *			- method 속성을 사용하여 HTTP 메서드를 매핑 조건으로 지정할 수 있다.
	 *			- 화면으로 응답하는 경우에는 HTTP 메서드로 GET방식과 POST방식 두 가지를 사용할 수 있다.
	 */
	
	// HTTP 메서드 매핑 실행 페이지
	
	@RequestMapping(value = "/formHome", method = RequestMethod.GET)
	public String formHome() {
		log.info("formHome() 실행...!");
		return "formHome";
	}
	
	// register 경로에 GET 방식
	@RequestMapping(value = "/http/register", method = RequestMethod.GET)
	public String registerFormHttp() {
		log.info("registerFormHttp() 실행...! GET 방식으로 요청");
		return "success";
	}
	
	// register 경로에 POST 방식
	@RequestMapping(value = "/http/register", method = RequestMethod.POST)
	public String registerHttp() {
		log.info("registerHttp() 실행...!");
		return "success";
	}
	
	// modify 경로에  GET 방식
	@RequestMapping(value = "/http/modify", method = RequestMethod.GET)
	public String modifyFormHttp() {
		log.info("modifyFormHttp() 실행...! GET 방식으로 요청");
		return "success";
	}
	
	// modify 경로에 POST 방식
	@RequestMapping(value = "/http/modify", method = RequestMethod.POST)
	public String modifyHttp() {
		log.info("modifyHttp() 실행...!");
		return "success";
	}
	
	// remove 경로에 POST 방식
	@RequestMapping(value = "/http/remove", method = RequestMethod.POST)
	public String removeHttp() {
		log.info("removeHttp() 실행...!");
		return "success";
	}
	
	// list 경로에 GET 방식
	@RequestMapping(value = "/http/list", method = RequestMethod.GET)
	public String listHttp() {
		log.info("listHttp() 실행...!");
		return "success";
	}
	
}

[success.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>SUCCESS</title>
	</head>
	<body>
		<h3>SUCCESS!</h3>
	</body>
</html>

- http://localhost/board/formHome


package kr.or.ddit.controller.board;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

@Controller
@RequestMapping("/board")
public class BoardController {

	/*
	 * [ 3장 : 컨트롤러 요청 매핑 ]
	 * 
	 * 		1. 요청 경로 매핑
	 * 
	 * 			- @RequestMapping의 value 속성에 요청 경로를 설정한다.
	 * 			- 요청 경로는 반드시 설정해야 하는 필수 정보이다.
	 * 			- 속성이 하나일 때는 속성명을 생략할 수 있다. (default는 value)
	 * 			- 컨트롤러의 클래스 레벨과 메서드 레벨로 지정할 수 있다.
	 * 			- 클래스 레벨로 요청 경로를 지정하면 메서드 레벨에서 지정한 경로의 기본 경로로 취급된다.
	 * 			- 클래스 레벨의 요청 경로에 메서드 레벨의 요청 경로를 덧붙인 형태가 최종 경로가 된다.
	 */
	
	private static final Logger log = LoggerFactory.getLogger(BoardController.class);
	
	@RequestMapping(value = "/register")
	public void registerForm() {
		log.info("registerForm() 실행...!");
	}
	
	@RequestMapping(value = "/modify")
	public void modifyForm() {
		log.info("modifyForm() 실행...!");
	}
	
	@RequestMapping(value = "/list")
	public void list() {
		log.info("list() 실행...!");
	}
	
	/*
	 * 		2. 경로 패턴 매핑
	 * 
	 * 			- 요청 경로를 동적으로 표현이 가능한 경로 패턴을 지정할 수 있다.
	 * 			- URL 경로 상의 변하는 값을 경로 변수로 취급한다.
	 * 			- 경로 변수에 해당하는 값을 파라미터 변수에 설정할 수 있다.
	 */
	
	@RequestMapping(value = "/read/{boardNo}")
	public String read(@PathVariable("boardNo") int boardNo) {
		log.info("read() 실행...!");
		log.info("경로 상의 포함된 boardNo : " + boardNo);
		return "board/read";
	}
	
	/*
	 *		3. HTTP 메서드 매핑
	 *
	 *			- method 속성을 사용하여 HTTP 메서드를 매핑 조건으로 지정할 수 있다.
	 *			- 화면으로 응답하는 경우에는 HTTP 메서드로 GET방식과 POST방식 두 가지를 사용할 수 있다.
	 */
	
	// HTTP 메서드 매핑 실행 페이지
	
	@RequestMapping(value = "/formHome", method = RequestMethod.GET)
	public String formHome() {
		log.info("formHome() 실행...!");
		return "formHome";
	}
	
	// register 경로에 GET 방식
	@RequestMapping(value = "/http/register", method = RequestMethod.GET)
	public String registerFormHttp() {
		log.info("registerFormHttp() 실행...! GET 방식으로 요청");
		return "success";
	}
	
	// register 경로에 POST 방식
	@RequestMapping(value = "/http/register", method = RequestMethod.POST)
	public String registerHttp() {
		log.info("registerHttp() 실행...!");
		return "success";
	}
	
	// modify 경로에  GET 방식
	@RequestMapping(value = "/http/modify", method = RequestMethod.GET)
	public String modifyFormHttp() {
		log.info("modifyFormHttp() 실행...! GET 방식으로 요청");
		return "success";
	}
	
	// modify 경로에 POST 방식
	@RequestMapping(value = "/http/modify", method = RequestMethod.POST)
	public String modifyHttp() {
		log.info("modifyHttp() 실행...!");
		return "success";
	}
	
	// remove 경로에 POST 방식
	@RequestMapping(value = "/http/remove", method = RequestMethod.POST)
	public String removeHttp() {
		log.info("removeHttp() 실행...!");
		return "success";
	}
	
	// list 경로에 GET 방식
	@RequestMapping(value = "/http/list", method = RequestMethod.GET)
	public String listHttp() {
		log.info("listHttp() 실행...!");
		return "success";
	}
	
	/*
	 * 		4. Params 매핑
	 * 
	 * 			- 요청 파라미터를 매핑 조건으로 지정하는 경우에는 params 속성을 사용한다.
	 * 			- 버튼이나 링크에 따라 호출할 메서드를 바꿔야 할 때 사용한다.
	 * 
	 * 			** Params 매핑 테스트 페이지
	 * 				> board/list.jsp
	 * 				> board/modify.jsp
	 * 				> board/read.jsp
	 * 				> board/register.jsp
	 * 				> board/remove.jsp
	 */
	
	// /board/get 경로, GET 방식, "register" 요청 파라미터에 대한 처리
	@RequestMapping(value = "/get", method = RequestMethod.GET, params = "register")
	public String registerFormParamsGet() {
		log.info("registerFormParamsGet() 실행...!");
		return "board/register";
	}
	
}

[list.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>BOARD</title>
	</head>
	<body>
		<h3>LIST</h3>
		
		<a href="/board/get?register">Register</a>
		<a href="/board/get?read">Read</a>
	</body>
</html>

- http://localhost/board/list


package kr.or.ddit.controller.board;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

@Controller
@RequestMapping("/board")
public class BoardController {

	/*
	 * [ 3장 : 컨트롤러 요청 매핑 ]
	 * 
	 * 		1. 요청 경로 매핑
	 * 
	 * 			- @RequestMapping의 value 속성에 요청 경로를 설정한다.
	 * 			- 요청 경로는 반드시 설정해야 하는 필수 정보이다.
	 * 			- 속성이 하나일 때는 속성명을 생략할 수 있다. (default는 value)
	 * 			- 컨트롤러의 클래스 레벨과 메서드 레벨로 지정할 수 있다.
	 * 			- 클래스 레벨로 요청 경로를 지정하면 메서드 레벨에서 지정한 경로의 기본 경로로 취급된다.
	 * 			- 클래스 레벨의 요청 경로에 메서드 레벨의 요청 경로를 덧붙인 형태가 최종 경로가 된다.
	 */
	
	private static final Logger log = LoggerFactory.getLogger(BoardController.class);
	
	@RequestMapping(value = "/register")
	public void registerForm() {
		log.info("registerForm() 실행...!");
	}
	
	@RequestMapping(value = "/modify")
	public void modifyForm() {
		log.info("modifyForm() 실행...!");
	}
	
	@RequestMapping(value = "/list")
	public void list() {
		log.info("list() 실행...!");
	}
	
	/*
	 * 		2. 경로 패턴 매핑
	 * 
	 * 			- 요청 경로를 동적으로 표현이 가능한 경로 패턴을 지정할 수 있다.
	 * 			- URL 경로 상의 변하는 값을 경로 변수로 취급한다.
	 * 			- 경로 변수에 해당하는 값을 파라미터 변수에 설정할 수 있다.
	 */
	
	@RequestMapping(value = "/read/{boardNo}")
	public String read(@PathVariable("boardNo") int boardNo) {
		log.info("read() 실행...!");
		log.info("경로 상의 포함된 boardNo : " + boardNo);
		return "board/read";
	}
	
	/*
	 *		3. HTTP 메서드 매핑
	 *
	 *			- method 속성을 사용하여 HTTP 메서드를 매핑 조건으로 지정할 수 있다.
	 *			- 화면으로 응답하는 경우에는 HTTP 메서드로 GET방식과 POST방식 두 가지를 사용할 수 있다.
	 */
	
	// HTTP 메서드 매핑 실행 페이지
	
	@RequestMapping(value = "/formHome", method = RequestMethod.GET)
	public String formHome() {
		log.info("formHome() 실행...!");
		return "formHome";
	}
	
	// register 경로에 GET 방식
	@RequestMapping(value = "/http/register", method = RequestMethod.GET)
	public String registerFormHttp() {
		log.info("registerFormHttp() 실행...! GET 방식으로 요청");
		return "success";
	}
	
	// register 경로에 POST 방식
	@RequestMapping(value = "/http/register", method = RequestMethod.POST)
	public String registerHttp() {
		log.info("registerHttp() 실행...!");
		return "success";
	}
	
	// modify 경로에  GET 방식
	@RequestMapping(value = "/http/modify", method = RequestMethod.GET)
	public String modifyFormHttp() {
		log.info("modifyFormHttp() 실행...! GET 방식으로 요청");
		return "success";
	}
	
	// modify 경로에 POST 방식
	@RequestMapping(value = "/http/modify", method = RequestMethod.POST)
	public String modifyHttp() {
		log.info("modifyHttp() 실행...!");
		return "success";
	}
	
	// remove 경로에 POST 방식
	@RequestMapping(value = "/http/remove", method = RequestMethod.POST)
	public String removeHttp() {
		log.info("removeHttp() 실행...!");
		return "success";
	}
	
	// list 경로에 GET 방식
	@RequestMapping(value = "/http/list", method = RequestMethod.GET)
	public String listHttp() {
		log.info("listHttp() 실행...!");
		return "success";
	}
	
	/*
	 * 		4. Params 매핑
	 * 
	 * 			- 요청 파라미터를 매핑 조건으로 지정하는 경우에는 params 속성을 사용한다.
	 * 			- 버튼이나 링크에 따라 호출할 메서드를 바꿔야 할 때 사용한다.
	 * 
	 * 			** Params 매핑 테스트 페이지
	 * 				> board/list.jsp
	 * 				> board/modify.jsp
	 * 				> board/read.jsp
	 * 				> board/register.jsp
	 * 				> board/remove.jsp
	 */
	
	// /board/get 경로, GET 방식, "register" 요청 파라미터에 대한 처리
	@RequestMapping(value = "/get", method = RequestMethod.GET, params = "register")
	public String registerFormParamsGet() {
		log.info("registerFormParamsGet() 실행...!");
		return "board/register";
	}
	
	// /board/post 경로, POST 방식, "register" 요청 파라미터에 대한 처리
	@RequestMapping(value = "/post", method = RequestMethod.POST, params = "register")
	public String registerParamsPost() {
		log.info("registerParamsPost() 실행...!");
		return "board/list";
	}
	
	// /board/get 경로, GET 방식, "modify" 요청 파라미터에 대한 처리
	@RequestMapping(value = "/get", method = RequestMethod.GET, params = "modify")
	public String modifyFormParamsGet() {
		log.info("modifyFormParamsGet() 실행...!");
		return "board/modify";
	}
	
	// /board/post 경로, POST 방식, "modify" 요청 파라미터에 대한 처리
	@RequestMapping(value = "/post", method = RequestMethod.POST, params = "modify")
	public String modifyParamsPost() {
		log.info("modifyParamsPost() 실행...!");
		return "board/list";
	}
	
	// /board/get 경로, GET 방식, "remove" 요청 파라미터에 대한 처리
	@RequestMapping(value = "/get", method = RequestMethod.GET, params = "remove")
	public String removeFormParamsGet() {
		log.info("removeFormParamsGet() 실행...!");
		return "board/remove";
	}
	
	// /board/post 경로, POST 방식, "remove" 요청 파라미터에 대한 처리
	@RequestMapping(value = "/post", method = RequestMethod.POST, params = "remove")
	public String removeParamsPost() {
		log.info("removeParamsPost() 실행...!");
		return "board/list";
	}
	
	// /board/list 경로, GET 방식, "list" 요청 파라미터에 대한 처리
	@RequestMapping(value = "/get", method = RequestMethod.GET, params = "list")
	public String listParamsGet() {
		log.info("listParamsGet() 실행...!");
		return "board/list";
	}
	
	// /board/read 경로, GET 방식, "read" 요청 파라미터에 대한 처리
	@RequestMapping(value = "/get", method = RequestMethod.GET, params = "read")
	public String readParamsGet() {
		log.info("readParamsGet() 실행...!");
		return "board/read";
	}
	
}

[modify.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>BOARD</title>
	</head>
	<body>
		<h3>MODIFY</h3>
		
		<form action="/board/post" method="post">
			<button type="submit" name="modify">Modify</button>
		</form>
		
		<a href="/board/get?list">List</a>
	</body>
</html>

[read.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>BOARD</title>
	</head>
	<body>
		<h3>READ</h3>
		
		<form action="/board/get" method="get">
			<button type="submit" name="modify">Modify</button>
			<button type="submit" name="remove">Remove</button>
		</form>
		
		<a href="/board/get?list">List</a>
	</body>
</html>

[register.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>BOARD</title>
	</head>
	<body>
		<h3>REGISTER</h3>
		
		<form action="/board/post" method="post">
			<button type="submit" name="register">Register</button>
		</form>
		
		<a href="/board/get?list">List</a>
	</body>
</html>

[remove.jsp]

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
	<head>
		<meta charset="UTF-8">
		<title>BOARD</title>
	</head>
	<body>
		<h3>REMOVE</h3>
		
		<form action="/board/post" method="post">
			<button type="submit" name="remove">Remove</button>
		</form>
		
		<a href="/board/get?list">List</a>
	</body>
</html>

- http://localhost/board/list