Dev/JSP & Servlet

Servlet - 게시판 만들기

창문닦이 2019. 2. 26. 21:59

Servlet을 활용한 게시판 만들기

기존에 만들어둔 board 테이블을 그대로 사용할 것이므로 DTO, DAO는 변동없음


http://localhost:8080/study/sboard/created.jsp 물리적인 주소를 서블릿을 이용하여 감출 것

http://localhost:8080/study/bbs/created.do bbs/이후는 무슨 단어가 오든 상관없음. 사용자정의

ContextPath : http://localhost:8080/study 에 해당


팀프로젝트 진행시 어떤 주소에 따라 어느 서블릿을 실행해야 하는지를 매핑하는 소스를 web.xml에 작성하고 합치면 된다.

web.xml

<!-- Servlet 게시판 -->

<servlet>

<servlet-name>boardServlet</servlet-name>

<servlet-class>com.board.BoardServlet</servlet-class>

</servlet>

<servlet-mapping>

<servlet-name>boardServlet</servlet-name>

<url-pattern>/bbs/*</url-pattern>

</servlet-mapping>


/bbs를 작성할경우 BoardServlet.java가 실행되도록 매핑 작업

bbs/뒤에 어떠한 단어가 오든 상관없이 연결을 할 수 있도록 *로 표시


Servlet클래스 구성

BoardServlet.java


Insert, Update, Delete, Session시에는 Redirect를 진행, 그 이외의 경우는 모두 forward 진행해야하므로

메소드로 호출하여 사용  

protected void forward(HttpServletRequest req, HttpServletResponse resp, String url) throws ServletException, IOException {

//forward

RequestDispatcher rd = req.getRequestDispatcher(url);

rd.forward(req, resp);

}


get방식에서도 동일하게 doPost 메소드 호출

@Override

protected void doGet(HttpServletRequest req, HttpServletResponse resp)

throws ServletException, IOException {

doPost(req, resp);

}


@Override

protected void doPost(HttpServletRequest req, HttpServletResponse resp)

throws ServletException, IOException {

//공통적으로 사용하는 변수 선언

req.setCharacterEncoding("UTF-8");

String cp = req.getContextPath(); //http://localhost:8080/프로젝트명

//DB연결

Connection conn = DBCPConn.getConnection();

BoardDAO dao = new BoardDAO(conn);

//페이징처리를 위한 객체 생성

MyUtil myUtil = new MyUtil();

// /프로젝트명/created.do 뒷부분의 주소를 읽어옴

String uri = req.getRequestURI();

String url;

//uri에 해당 단어가 있는지 확인

if(uri.indexOf("created.do")!=-1){

//게시글 작성시 실행소스

}else if(uri.indexOf("created_ok.do")!=-1){

//게시글 작성시 실행소스

}else if(uri.indexOf("list.do")!=-1){

//리스트 조회 실행소스

}else if(uri.indexOf("article.do")!=-1){

//게시글 조회 실행소스

}else if(uri.indexOf("updated.do")!=-1){

//게시글 수정 실행소스

}else if(uri.indexOf("updated_ok.do")!=-1){

//게시글 수정 실행소스

}else if(uri.indexOf("deleted_ok.do")!=-1){

//게시글 삭제 실행소스

}


작성한 주소에 붙는 입력값(uri)에 따른 페이지 호출을 if문으로 작성하여 실행되는 dao의 메소드를 다르게 호출


}


Servlet 클래스 

BoardServlet.java

//uri에 해당 단어가 있는지 확인

if(uri.indexOf("created.do")!=-1){

url= "/sboard/created.jsp";

forward(req, resp, url);

}else if(uri.indexOf("created_ok.do")!=-1){

BoardDTO dto = new BoardDTO();

int maxNum = dao.getMaxNum();

dto.setNum(maxNum+1);

dto.setSubject(req.getParameter("subject"));

dto.setName(req.getParameter("name"));

dto.setEmail(req.getParameter("email"));

dto.setPwd(req.getParameter("pwd"));

dto.setContent(req.getParameter("content"));

dto.setIpAddr(req.getRemoteAddr());

dao.insertData(dto);

//redirect 진행

url = cp+"/bbs/list.do";

resp.sendRedirect(url);

}else if(uri.indexOf("list.do")!=-1){

String pageNum = req.getParameter("pageNum");

int currentPage = 1; //처음 띄우는 리스트 페이지

if(pageNum!=null){

currentPage = Integer.parseInt(pageNum);

}

String searchKey = req.getParameter("searchKey");

String searchValue = req.getParameter("searchValue");

if(searchValue==null || searchValue.equals(null)){

searchKey ="subject";

searchValue = "";

}else{

if(req.getMethod().equalsIgnoreCase("GET")){

searchValue = URLDecoder.decode(searchValue, "UTF-8");

}

}

int dataCount = dao.getDataCount(searchKey, searchValue);

int numPerPage = 10;

int totalPage = myUtil.getPageCount(numPerPage, dataCount);

if(currentPage>totalPage)

currentPage = totalPage;

int start = (currentPage-1)*numPerPage+1;

int end = currentPage*numPerPage;

List<BoardDTO> lists = dao.getLists(start, end, searchKey, searchValue);

String param = "";

if(!searchValue.equals("")){

param = "searchKey=" + searchKey;

param += "&searchValue=" + URLEncoder.encode(searchValue,"UTF-8");

}

String listUrl = cp+"/bbs/list.do";

if(!param.equals("")){

listUrl +="?" + param;

}

String pageIndexList = myUtil.pageIndexList(currentPage, totalPage, listUrl);

String articleUrl = cp + "/bbs/article.do?pageNum=" + currentPage;

if(!param.equals("")){

articleUrl += "&" + param;

}

//포워딩할 데이터

req.setAttribute("lists", lists);

req.setAttribute("pageIndexList", pageIndexList);

req.setAttribute("articleUrl", articleUrl);

req.setAttribute("dataCount", dataCount);

url = "/sboard/list.jsp";

forward(req, resp, url);

}else if(uri.indexOf("article.do")!=-1){

int num = Integer.parseInt(req.getParameter("num"));

String pageNum = req.getParameter("pageNum");

String searchKey = req.getParameter("searchKey");

String searchValue = req.getParameter("searchValue");

if(searchValue!=null){

searchValue = URLDecoder.decode(searchValue, "UTF-8");

}

//조회수 증가

dao.updateHitCount(num);

//게시판 내용 읽기

BoardDTO dto = dao.getReadData(num);

//게시판 해당 내용 없을 경우 redirect

if(dto==null){

url = cp + "/bbs/list.do";

resp.sendRedirect(url);

}

//내용출력

int lineSu = dto.getContent().split("\n").length;

dto.setContent(dto.getContent().replaceAll("\n", "<br/>"));

String param = "pageNum="+pageNum;

if(searchValue!=null){

param += "&searchKey=" + searchKey;

param += "&searchValue=" + URLEncoder.encode(searchValue,"UTF-8");

}

req.setAttribute("dto", dto);

req.setAttribute("params", param);

req.setAttribute("lineSu", lineSu);


//포워드 진행

url = "/sboard/article.jsp";

forward(req, resp, url);

}else if(uri.indexOf("updated.do")!=-1){

int num = Integer.parseInt(req.getParameter("num"));

String pageNum = req.getParameter("pageNum");

String searchKey = req.getParameter("searchKey");

String searchValue = req.getParameter("searchValue");

if(searchValue!=null){

searchValue =URLDecoder.decode(searchValue, "UTF-8");

}


//게시판 내용 읽기

BoardDTO dto = dao.getReadData(num);

if(dto==null){

url = cp + "/bbs/list.do";

resp.sendRedirect(url);

}

String param = "pageNum="+pageNum;

if(searchValue!=null){

param += "&searchKey=" + searchKey;

param += "&searchValue=" + URLEncoder.encode(searchValue,"UTF-8");

}

req.setAttribute("dto", dto);

req.setAttribute("pageNum", pageNum);

req.setAttribute("params", param);


//포워드 진행

url = "/sboard/updated.jsp";

forward(req, resp, url);

}else if(uri.indexOf("updated_ok.do")!=-1){

String params = req.getParameter("params");

//action쓸수없음

BoardDTO dto = new BoardDTO();

dto.setNum(Integer.parseInt(req.getParameter("num")));

dto.setSubject(req.getParameter("subject"));

dto.setName(req.getParameter("name"));

dto.setEmail(req.getParameter("email"));

dto.setPwd(req.getParameter("pwd"));

dto.setContent(req.getParameter("content"));

                        //게시글 수정

dao.updateData(dto);


//게시판 수정 완료 후 리스트 페이지로 redirect

url = cp + "/bbs/list.do?"+params;

resp.sendRedirect(url);

}else if(uri.indexOf("deleted_ok.do")!=-1){

int num = Integer.parseInt(req.getParameter("num"));

String pageNum = req.getParameter("pageNum");

String searchKey = req.getParameter("searchKey");

String searchValue = req.getParameter("searchValue");

if(searchValue!=null){

searchValue = URLDecoder.decode(searchValue, "UTF-8");

}

String param = "pageNum="+pageNum;

if(searchValue!=null){

param += "&searchKey=" + searchKey;

param += "&searchValue=" + URLEncoder.encode(searchValue,"UTF-8");

}

                        //게시글 삭제

dao.deleteData(num);


//게시판 삭제 완료 후 리스트 페이지로 redirect

url = cp + "/bbs/list.do?"+param;

resp.sendRedirect(url);

}

}






톰캣 서버의 캐시가 기록된 내용으로 인한 충돌이 생길 수 있음. 그럴 경우 clean tomcat work directory 진행.


게시글 조회 페이지(article.jsp)

article.jsp

<%@ page contentType="text/html; charset=UTF-8"%>

<%

request.setCharacterEncoding("UTF-8");

String cp = request.getContextPath();

%>

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">

<html>

<head>

<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">

<title>게 시 판(Servlet)</title>

<link rel="stylesheet" href="<%=cp %>/sboard/css/style.css" type="text/css" />

<link rel="stylesheet" href="<%=cp %>/sboard/css/article.css" type="text/css" />

</head>

<body>

<div id="bbs">

<div id="bbs_title">

게 시 판(Servlet)

</div>

<div id="bbsArticle">

<div id="bbsArticle_header">

${dto.subject }

</div>

<div class="bbsArticle_bottomLine">

<dl>

<dt>작성자</dt>

<dd>${dto.name }</dd>

<dt>줄수</dt>

<dd>${lineSu }</dd>

</dl>

</div>

<div class="bbsArticle_bottomLine">

<dl>

<dt>등록일</dt>

<dd>${dto.created }</dd>

<dt>조회수</dt>

<dd>${dto.hitCount }</dd>

</dl>

</div>

<div id="bbsArticle_content">

<table width="600" border="0">

<tr>

<td style="padding: 20px 80px 20px 62px;" valign="top" height="200">

${dto.content }

</td>

</tr>

</table>

</div>

</div>

<div class="bbsArticle_noLine" style="text-align: right;">

from : ${dto.ipAddr }

</div>

<div id="bbsArticle_footer">

<div id="leftFooter">

<input type="button" value=" 수정 " class="btn2"

onclick="javascript:location.href='<%=cp %>/bbs/updated.do?num=${dto.num }&${params }';" />

<input type="button" value=" 삭제 " class="btn2"

onclick="javascript:location.href='<%=cp %>/bbs/deleted_ok.do?num=${dto.num }&${params }';" />

</div>

<div id="rightFooter">

<input type="button" value=" 리스트 " class="btn2"

onclick="javascript:location.href='<%=cp %>/bbs/list.do?${params }';" />

</div>

</div>

</div>

</body>

</html>




게시글 작성 페이지(created.jsp)

created.jsp

<%@ page contentType="text/html; charset=UTF-8"%>

<%

request.setCharacterEncoding("UTF-8");

String cp = request.getContextPath();

%>

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">

<html>

<head>

<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">

<title>게 시 판(Servlet)</title>

<link rel="stylesheet" href="<%=cp %>/sboard/css/style.css" type="text/css" />

<link rel="stylesheet" href="<%=cp %>/sboard/css/created.css" type="text/css" />

<script type="text/javascript" src="<%=cp %>/sboard/js/util.js"></script>

<script type="text/javascript" >

function sendIt(){

f = document.myForm;

str = f.subject.value;

str = str.trim();//util.js에 있는 trim함수 호출

if(!str){

alert("\n제목을 입력하세요.");//공백제거후 내용이 없으면

f.subject.focus();

return;

}

f.subject.value = str;

str = f.name.value;

str = str.trim();

if(!str){

alert("\n이름을 입력하세요.");

f.name.focus();

return;

}

f.name.value = str;

/*

//이름 한글검사

if(!isValidKorean(str)){

alert("\n이름을 정확히 입력하세요.");

f.name.focus();

return;

}

*/

if(f.email.value){

if(!isValidEmail(f.email.value)){

alert("\n정상적인 E-mail을 입력하세요");

f.email.focus();

return;

}

}

str = f.content.value;

str = str.trim();

if(!str){

alert("\n내용을 입력하세요.");

f.content.focus();

return;

}

f.content.value = str;

str = f.pwd.value;

str = str.trim();

if(!str){

alert("\n패스워드를 입력하세요.");

f.pwd.focus();

return;

}

f.pwd.value = str;

f.action = "<%=cp %>/bbs/created_ok.do";

f.submit();

}

</script>

</head>

<body>

<div id="bbs" >

<div id="bbs_title">

게 시 판(Servlet)

</div>

<form action="" name="myForm" method="post">

<div id="bbsCreated">

<div class="bbsCreated_bottomLine">

<dl>

<dt>제&nbsp;&nbsp;&nbsp;&nbsp;목</dt>

<dd>

<input type="text" name="subject" size="74" maxlength="100" class="boxTF"/>

</dd>

</dl>

</div>

<div class="bbsCreated_bottomLine">

<dl>

<dt>작성자</dt>

<dd>

<input type="text" name="name" size="35" maxlength="20" class="boxTF"/>

</dd>

</dl>

</div>

<div class="bbsCreated_bottomLine">

<dl>

<dt>E-Mail</dt>

<dd>

<input type="text" name="email" size="35" maxlength="50" class="boxTF"/>

</dd>

</dl>

</div>

<div id="bbsCreated_content">

<dl>

<dt>내&nbsp;&nbsp;&nbsp;&nbsp;용</dt>

<dd>

<textarea rows="12" cols="63" name="content" class="boxTA"></textarea>

</dd>

</dl>

</div>

<div class="bbsCreated_noLine">

<dl>

<dt>패스워드</dt>

<dd>

<input type="password" name="pwd" size="35" maxlength="7" class="boxTF"/>

&nbsp;(게시물 수정 및 삭제시 필요)

</dd>

</dl>

</div>

</div>

<div id="bbsCreated_footer">

<input type="button" value="등록하기" class="btn2"

onclick="sendIt();" />

<input type="reset" value="다시입력" class="btn2"

onclick="document.myForm.subject.focus();" />

<input type="button" value="작성취소" class="btn2"

onclick="javascript:location.href='<%=cp %>/bbs/list.do';" />

</div>

</form>

</div>

</body>

</html>





게시글 수정 페이지(updated.jsp)

updated.jsp

<body>

<div id="bbs" >

<div id="bbs_title">

게 시 판(Servlet)

</div>

<form action="" name="myForm" method="post">

<div id="bbsCreated">

<div class="bbsCreated_bottomLine">

<dl>

<dt>제&nbsp;&nbsp;&nbsp;&nbsp;목</dt>

<dd>

<input type="text"name="subject" value="${dto.subject}"size="74"maxlength="100" class="boxTF"/>

</dd>

</dl>

</div>

<div class="bbsCreated_bottomLine">

<dl>

<dt>작성자</dt>

<dd>

<input type="text" name="name" value="${dto.name}" size="35" maxlength="20" class="boxTF"/>

</dd>

</dl>

</div>

<div class="bbsCreated_bottomLine">

<dl>

<dt>E-Mail</dt>

<dd>

<input type="text" name="email" value="${dto.email}"size="35" maxlength="50" class="boxTF"/>

</dd>

</dl>

</div>

<div id="bbsCreated_content">

<dl>

<dt>내&nbsp;&nbsp;&nbsp;&nbsp;용</dt>

<dd>

<textarea rows="12" cols="63" name="content" class="boxTA">${dto.content}</textarea>

</dd>

</dl>

</div>

<div class="bbsCreated_noLine">

<dl>

<dt>패스워드</dt>

<dd>

<input type="password"name="pwd" value="${dto.pwd}" size="35" maxlength="7" class="boxTF"/>

&nbsp;(게시물 수정 및 삭제시 필요)

</dd>

</dl>

</div>

</div>

<div id="bbsCreated_footer">

<input type="hidden" name="num" value="${dto.num }">

<input type="button" value="수정하기" class="btn2"

onclick="sendIt();" />

<input type="button" value="수정취소" class="btn2"

onclick="javascript:location.href='<%=cp %>/bbs/list.do?${params }';" />

</div>

</form>

</div>

</body>


게시물 리스트 조회 페이지(list.jsp)

list.jsp

<%@ page contentType="text/html; charset=UTF-8"%>

<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>

<%

request.setCharacterEncoding("UTF-8");

String cp = request.getContextPath();

%>

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">

<html>

<head>

<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">

<title>게 시 판(Servlet)</title>

<link rel="stylesheet" href="<%=cp %>/sboard/css/style.css" type="text/css" />

<link rel="stylesheet" href="<%=cp %>/sboard/css/list.css" type="text/css" />

<script type="text/javascript">

function sendIt(){

var f = document.searchForm;

f.action = "<%=cp %>/bbs/list.do"; //검색 버튼을 누를경우 파라미터값과 함께 리스트페이지로 이동

f.submit();

}

</script>

</head>

<body>

<div id="bbsList">

<div id="bbsList_title">

게 시 판(Servlet)

</div>

<div id="bbsList_header">

<div id="leftHeader">

<form action="" name="searchForm" method="post">

<select name="searchKey" class="selectField">

<option value="subject">제목</option>

<option value="name">작성자</option>

<option value="content">내용</option>

</select>

<input type="text" name="searchValue" class="textField"/>

<input type="button" value="검  색" class="btn2" onclick="sendIt();"/>

</form>

</div>

<div id="rightHeader">

<input type="button" value=" 글올리기 " class="btn2"

onclick="javascript:location.href='<%=cp %>/bbs/created.do';" />

</div>

</div>

<div id="bbsList_list">

<div id="title">

<dl>

<dt class="num">번호</dt>

<dt class="subject">제목</dt>

<dt class="name">작성자</dt>

<dt class="created">작성일</dt>

<dt class="hitCount">조회수</dt>

</dl>

</div>

<div id="lists">

<c:forEach var="dto" items="${lists }">

<dl>

<dd class="num">${dto.num }</dd>

<dd class="subject">

<a href="${articleUrl}&num=${dto.num }">${dto.subject }</a>

</dd>

<dd class="name">${dto.name }</dd>

<dd class="created">${dto.created }</dd>

<dd class="hitCount">${dto.hitCount }</dd>

</dl>

</c:forEach>

</div>

<div id="footer">

<p>

<c:if test="${dataCount!=0 }">

${pageIndexList }

</c:if>

<c:if test="${dataCount==0 }">

등록된 게시물이 없습니다

</c:if>

</p>

</div>

</div>

</div>

</body>

</html>