본문 바로가기

Spring 3.0 - 4.3

Spring DAO 를 이용한 게시판 만들기

1탄. JDBC - SPRING DAO로 게시판 만들기 (spring dao)
2탄. JDBC - MyBatis로 게시판 만들기 (spring + mybatis)

 

 

 

 

프로젝트 생성

- 프로젝트명: Springweb / 패키지명: com.jdbc.springweb

 

 

기존에 만들어지는 Homecontroller, home.jsp 삭제하고 시작하기

 

ServletBoard(게시판 servlet버전 기본 틀).zip
0.01MB

 

(ServletBoard.zip 참고)

이전에 Servlet으로 만들었던 게시판 (_ok.jsp가 없는 구조) 을 가지고와서 Spring DAO로 게시판을 만드는 버전을 만들 것이다.

*회사에서는 com.board 폴더에 한꺼번에 넣지 않고 dao ,dto ,servlet 만 따로 모아두는 패키지를 만든다.

 

 

ServletBoard.zip 에서 가져올 소스파일 간단하게 정리 (이 외에 더 있음) - sts로 어떻게 옮기는 지 방식도 기억해두기

 

1. [ src>resources ] css,js폴더끌고오기

 

2. [ src> main > webapp > WEB-INF > views ]  bbs 폴더 copy ( 내부 jsp파일 불러오는것) 

 

 

3. .jsp 파일에서 불러온 css, js 경로 수정해주기

// Servlet 사용 때의 경로
<link rel="stylesheet" href="<%=cp%>/bbs/css/style.css" type="text/css"/>
// Spring DAO 사용 때의 경로
<link rel="stylesheet" href="/springweb/resources/css/style.css" type="text/css"/>

 

4. 확장자 바꿔주기

- servlet은 기본 확장자가 .do 이고 spring은 기본 확장자가 .action 

<!-- Servlet에서의 경로 -->
.href='<%=cp%>/board/list.do?${params}'"/>
<!-- Spring DAO 에서의 경로 -->
.href='<%=cp%>/list.action?${params}'"/>

 

1. pom.xml 설정

Spring JDBC의 lib (DB사용하려면) 

<!-- Spring - JDBC -->
<dependency>
  <groupId>org.springframework</groupId>
  <artifactId>spring-jdbc</artifactId>
  <version>${org.springframework-version}</version>
</dependency>

+ servlet-context.xml 에도 템플릿 추가

 

JDBC의 lib

<!-- JDBC -->
<dependency>
    	<groupId>org.springframework</groupId>
    	<artifactId>spring-jdbc</artifactId>
    	<version>${spring.framework.version}</version>
</dependency>

그냥 JDBC로 했을때랑 Spring JDBC로 했을때랑 <version> 내부 모양이 다른 걸 볼 수 있음

 

2. servlet-context.xml

JdbcTemplate 이용

	<beans:bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
		<beans:property name="prefix" value="/WEB-INF/views/" />
		<beans:property name="suffix" value=".jsp" />
	</beans:bean>
	
	<context:component-scan base-package="com.jdbc.springweb" />
	
	
	<beans:bean id="boardDAO2" class="com.jdbc.dao.BoardDAO2">
		<beans:property name="jdbcTemplate" ref="jdbcTemplate"/>
	</beans:bean>
	
	<beans:bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
		<beans:constructor-arg ref="dataSource"/>
	</beans:bean>
	
	<!-- DB정보 -->
	<beans:bean  id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close">
		<beans:property name="driverClassName" value="oracle.jdbc.driver.OracleDriver"/> 
		<beans:property name="url" value="jdbc:oracle:thin:@192.168.16.14:1521:TestDBB"/>
		<beans:property name="username" value="suzi"/> 
		<beans:property name="password" value="a123"/>
	</beans:bean>
	
	<beans:bean id="myUtil" class="com.jdbc.util.MyUtil"/>

DataSource -> JdbcTemplate -> BoardDAO2 의존성 주입

 

3. BoardDTO

package com.jdbc.dto;

public class BoardDTO {
	
	private int num;
	private String name,pwd,email,subject,content,ipAddr,created;
	private int hitCount;
    
    //getter, setter 생성
    
    }

 

4. BoardDAO

(1) - JdbcTemplate을 이용하지 않고 DB연결하여 DAO 생성하는 경우

servlet-context.xml 을 다음과 같이 생성 (DB정보를 BoardDAO에 의존성 주입)

	<beans:bean id="boardDAO" class="com.jdbc.dao.BoardDAO">
		<beans:property name="dataSource" ref="dataSource"/>
	</beans:bean>
	
	<!-- DB정보 -->
	<beans:bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close">
		<beans:property name="driverClassName" value="oracle.jdbc.driver.OracleDriver"/> 
		<beans:property name="url" value="jdbc:oracle:thin:@192.168.16.14:1521:TestDBB"/>
		<beans:property name="username" value="suzi"/> 
		<beans:property name="password" value="a123"/>
	</beans:bean>
	
	<beans:bean id="myUtil" class="com.jdbc.util.MyUtil"/>

 

BoardDAO.java - 원래 하던 방식대로 sql문 생성해서 DB에 접근

package com.jdbc.dao;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.ArrayList;
import java.util.List;

import javax.sql.DataSource;

import com.jdbc.dto.BoardDTO;


public class BoardDAO {
	
	private DataSource datasource;
	
	public void setDataSource(DataSource datasource)
				throws Exception {
		this.datasource = datasource;
		
		//원래는 이 메소드 바깥에서 dataSource로부터 connection을 얻어내는건데 
		// 이 예제에서는 이 안에다가 써도 됨
		conn = datasource.getConnection();
		
	} 
		
	Connection conn = null; 
	
	//1.num의 최대값
	public int getMaxNum(){
		
		int maxNum = 0;
		PreparedStatement pstmt = null;
		ResultSet rs = null;
		String sql;
		
		try {
			
			sql = "select nvl(max(num),0) from board";
			
			pstmt = conn.prepareStatement(sql);
			rs = pstmt.executeQuery();
			
			if(rs.next())
				maxNum = rs.getInt(1);
			
			rs.close();
			pstmt.close();
			
		} catch (Exception e) {
			System.out.println(e.toString());
		}
		
		return maxNum;
		
	}
	
	public int insertData(BoardDTO dto){
		
		int result = 0;
		PreparedStatement pstmt = null;
		String sql;
		
		try {
			
			sql = "insert into board (num,name,pwd,email,subject,content,";
			sql+= "ipAddr,hitCount,created) ";
			sql+= "values(?,?,?,?,?,?,?,0,sysdate)";
			
			pstmt = conn.prepareStatement(sql);
			
			pstmt.setInt(1, dto.getNum());
			pstmt.setString(2, dto.getName());
			pstmt.setString(3, dto.getPwd());
			pstmt.setString(4, dto.getEmail());
			pstmt.setString(5, dto.getSubject());
			pstmt.setString(6, dto.getContent());
			pstmt.setString(7, dto.getIpAddr());
			
			result = pstmt.executeUpdate();
			
			pstmt.close();			
			
		} catch (Exception e) {
			System.out.println(e.toString());
		}
		return result;
		
	}
	
	//전체데이터
	public List<BoardDTO> getList(int start, int end,
			String searchKey, String searchValue){
		
		List<BoardDTO> lists = new ArrayList<BoardDTO>();
		PreparedStatement pstmt = null;
		ResultSet rs = null;
		String sql;
		
		try {
			
			searchValue = "%" + searchValue + "%";
			
			sql = "select * from (";
			sql+= "select rownum rnum,data.* from(";
			sql+= "select num,name,subject,hitCount,";
			sql+= "to_char(created,'YYYY-MM-DD') created ";
			sql+= "from board where " + searchKey + " like ? order by num desc) data) ";
			sql+= "where rnum >= ? and rnum <= ?";
			
			pstmt = conn.prepareStatement(sql);
			
			pstmt.setString(1, searchValue);
			pstmt.setInt(2, start);
			pstmt.setInt(3, end);
			
			rs = pstmt.executeQuery();
			
			while(rs.next()){
				
				BoardDTO dto = new BoardDTO();
				
				dto.setNum(rs.getInt("num"));
				dto.setName(rs.getString("name"));
				dto.setSubject(rs.getString("subject"));
				dto.setHitCount(rs.getInt("hitCount"));
				dto.setCreated(rs.getString("created"));
				
				lists.add(dto);
				
			}
			
			rs.close();
			pstmt.close();
			
		} catch (Exception e) {
			System.out.println(e.toString());
		}
		
		return lists;
		
	}
	
	//전체 데이터수 구하기
	public int getDataCount(String searchKey,String searchValue){
		
		int result = 0;
		
		PreparedStatement pstmt = null;
		ResultSet rs = null;
		String sql;
		
		try {
			
			searchValue = "%" + searchValue + "%";
			
			sql = "select nvl(count(*),0) from board ";
			sql+= "where " + searchKey + " like ?";
			
			pstmt = conn.prepareStatement(sql);
			
			pstmt.setString(1, searchValue);
			
			rs = pstmt.executeQuery();
			
			if(rs.next()){
				result = rs.getInt(1);
			}
			
			rs.close();
			pstmt.close();
			
		} catch (Exception e) {
			System.out.println(e.toString());
		}
		
		return result;
		
	}
	
	//조회수증가
	public int updateHitCount(int num){
		
		int result = 0;
		PreparedStatement pstmt = null;
		String sql;
		
		try {
			
			sql = "update board set hitCount=hitCount + 1 where num=?";
			
			pstmt = conn.prepareStatement(sql);
			pstmt.setInt(1, num);
			
			result = pstmt.executeUpdate();
			
			pstmt.close();
			
		} catch (Exception e) {
			System.out.println(e.toString());
		}
		
		return result;
		
	}
	
	//한명의 데이터 출력
	public BoardDTO getReadData(int num){
		
		BoardDTO dto = null;
		PreparedStatement pstmt = null;
		ResultSet rs = null;
		String sql;
		
		try {
			
			sql = "select num,name,pwd,email,subject,content,ipAddr,";
			sql+= "hitCount,created from board where num=?";
			
			pstmt = conn.prepareStatement(sql);
			pstmt.setInt(1, num);
			
			rs = pstmt.executeQuery();
			
			if(rs.next()){
				
				dto = new BoardDTO();
				
				dto.setNum(rs.getInt("num"));
				dto.setName(rs.getString("name"));
				dto.setPwd(rs.getString("pwd"));
				dto.setEmail(rs.getString("email"));
				dto.setSubject(rs.getString("subject"));
				dto.setContent(rs.getString("content"));
				dto.setIpAddr(rs.getString("ipAddr"));
				dto.setHitCount(rs.getInt("hitCount"));
				dto.setCreated(rs.getString("created"));				
				
			}
			
			rs.close();
			pstmt.close();
			
		} catch (Exception e) {			
			System.out.println(e.toString());			
		}
		
		return dto;
		
	}
	
	//삭제
	public int deleteData(int num){
		
		int result = 0;
		PreparedStatement pstmt = null;
		String sql;
		
		try {
			
			sql = "delete board where num=?";
			pstmt = conn.prepareStatement(sql);
			
			pstmt.setInt(1, num);
			
			result = pstmt.executeUpdate();
			
			pstmt.close();
			
		} catch (Exception e) {
			System.out.println(e.toString());
		}
		
		return result;
		
	}
	
	
	//수정
	public int updateData(BoardDTO dto){
		
		int result = 0;
		PreparedStatement pstmt = null;
		String sql;
		
		try {
			
			sql = "update board set name=?, pwd=?, email=?, subject=?,";
			sql+= "content=? where num=?";
			
			pstmt = conn.prepareStatement(sql);
			
			pstmt.setString(1, dto.getName());
			pstmt.setString(2, dto.getPwd());
			pstmt.setString(3, dto.getEmail());
			pstmt.setString(4, dto.getSubject());
			pstmt.setString(5, dto.getContent());
			pstmt.setInt(6, dto.getNum());
			
			result = pstmt.executeUpdate();
			
			pstmt.close();
			
		} catch (Exception e) {
			System.out.println(e.toString());
		}
		
		return result;
				
	}
	

}

 

 

(2) - JdbcTemplate을 이용하여 DAO 생성하는 경우

 

update, delete, insert문 -> jdbcTemplate.update(sql.toString(), 

select문 -> jdbcTemplate.query(sql.toString(),

 

BoardDAO2.java

package com.jdbc.dao;

import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.List;


import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.RowMapper;

import com.jdbc.dto.BoardDTO;


public class BoardDAO2 {

	private JdbcTemplate jdbcTemplate;

	public void setJdbcTemplate(JdbcTemplate jdbcTemplate)
			throws Exception {
		this.jdbcTemplate = jdbcTemplate;
	} 
	
	public int getMaxNum(){

		int maxNum = 0;
		StringBuilder sql = new StringBuilder();

		sql.append("select nvl(max(num),0) from board");

		maxNum = jdbcTemplate.queryForInt(sql.toString());


		return maxNum;

	}

	public void insertData(BoardDTO dto){

		StringBuilder sql = new StringBuilder();

		sql.append("insert into board (num,name,pwd,email,subject,content,")
		.append("ipAddr,hitCount,created) ")
		.append("values(?,?,?,?,?,?,?,0,sysdate)");


		jdbcTemplate.update(sql.toString(),
				dto.getNum(), dto.getName(), dto.getPwd(), dto.getEmail(),
				dto.getSubject(), dto.getContent(), 
				dto.getIpAddr()); 

	}


	public List<BoardDTO> getList(int start, int end,
			String searchKey, String searchValue){


		StringBuilder sql = new StringBuilder();

		searchValue = "%" + searchValue + "%";


		sql.append("select * from (")
		.append("select rownum rnum,data.* from(")
		.append("select num,name,subject,hitCount,")
		.append("to_char(created,'YYYY-MM-DD') created ")
		.append("from board where " + searchKey + " like ? order by num desc) data) ")
		.append("where rnum >= ? and rnum <= ?");

		List<BoardDTO> lists =
				jdbcTemplate.query(sql.toString(),
						new Object[] {searchValue,start,end}, // ? �닚�꽌 留욎떠二쇨린 洹� �븞�쑝濡� �뱾�뼱媛��뒗嫄곕땲源� 
						new RowMapper<BoardDTO>() { // 諛섎났臾� �떆�옉

					@Override
					public BoardDTO mapRow(ResultSet rs, 
							int rowNum) throws SQLException { // rowNum�뿉�뒗 �젅肄붾뱶�쓽 �씤�뜳�뒪踰덊샇媛� �뱾�뼱媛�

						BoardDTO dto = new BoardDTO();

						dto.setNum(rs.getInt("num"));
						dto.setName(rs.getString("name"));
						dto.setSubject(rs.getString("subject"));
						dto.setHitCount(rs.getInt("hitCount"));
						dto.setCreated(rs.getString("created"));

						return dto;
					}


				});

		return lists;

	}


	public int getDataCount(String searchKey,String searchValue){
		
		int result = 0;
		StringBuilder sql = new StringBuilder();

		searchValue = "%" + searchValue + "%";

		sql.append("select nvl(count(*),0) from board ");
		sql.append("where " + searchKey + " like ?");
		
		result = 
				jdbcTemplate.queryForInt(sql.toString(),searchValue);

		return result;
	}

	
	public void updateHitCount(int num){

		int result = 0;
		StringBuilder sql = new StringBuilder();
		
		sql.append("update board set hitCount=hitCount + 1 where num=?");
		
		jdbcTemplate.update(sql.toString(), num);
		

	}

	public BoardDTO getReadData(int num){
		
		StringBuilder sql = new StringBuilder();

		sql.append("select num,name,pwd,email,subject,content,ipAddr,")
			.append("hitCount,created from board where num=?");

		BoardDTO dtoOne  =
				jdbcTemplate.queryForObject(sql.toString(),
							new RowMapper<BoardDTO>() { // 諛섎났臾� �떆�옉
					
					@Override
					public BoardDTO mapRow(ResultSet rs, 
							int rowNum) throws SQLException { // rowNum�뿉�뒗 �젅肄붾뱶�쓽 �씤�뜳�뒪踰덊샇媛� �뱾�뼱媛�

						BoardDTO dto = new BoardDTO();

						dto.setNum(rs.getInt("num"));
						dto.setName(rs.getString("name"));
						dto.setPwd(rs.getString("pwd"));
						dto.setEmail(rs.getString("email"));
						dto.setSubject(rs.getString("subject"));
						dto.setContent(rs.getString("content"));
						dto.setIpAddr(rs.getString("ipAddr"));
						dto.setHitCount(rs.getInt("hitCount"));
						dto.setCreated(rs.getString("created"));				

						return dto;
					}


				}, num);
		
		
		return dtoOne;

	}

	
	public void deleteData(int num){
		
		StringBuilder sql = new StringBuilder();

		sql.append("delete board where num=?");

		jdbcTemplate.update(sql.toString(), num);

	}


	public void updateData(BoardDTO dto){

		StringBuilder sql = new StringBuilder();

		sql.append("update board set name=?, pwd=?, email=?, subject=?,")
		   .append("content=? where num=?");
		
		jdbcTemplate.update(sql.toString(),dto.getName(),
				dto.getPwd(),dto.getEmail(),dto.getSubject(),dto.getContent(),
				dto.getNum());

	}
	


}

 

 

5. jsp 파일

상단 css, js 경로 바꿔주기 

<link rel="stylesheet" href="/springweb/resources/css/style.css" type="text/css"/>
<link rel="stylesheet" href="/springweb/resources/css/created.css" type="text/css"/>

<script type="text/javascript" src="/springweb/resources/js/util.js"></script>

 

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>게 시 판</title>

<link rel="stylesheet" href="/springweb/resources/css/style.css" type="text/css"/>
<link rel="stylesheet" href="/springweb/resources/css/created.css" type="text/css"/>

<script type="text/javascript" src="/springweb/resources/js/util.js"></script>

<script type="text/javascript">

	function sendIt(){
		
		f = document.myForm;
		
		str = f.subject.value;
		str = str.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;
		}		
		/*
		if(!isValidKorean(str)){			
			alert("\n이름을 정확히 입력하세요.");
			f.name.focus();
			return;
		}
		*/
		f.name.value = str;
		
		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%>/created_ok.action";
		f.submit();
		
	}

</script>

</head>
<body>

<div id="bbs">
	<div id="bbs_title">
	게 시 판(spring)	
	</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"/>
				</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%>/list.action';"/>	
	</div>
	
	</form>
	
</div>

</body>
</html>

 

 

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>Insert title here</title>

<link rel="stylesheet" href="/springweb/resources/css/style.css" type="text/css"/>
<link rel="stylesheet" href="/springweb/resources/css/article.css" type="text/css"/>

</head>
<body>

<div id="bbs">
	<div id="bbs_title">
	게 시 판(Spring)
	</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%>/updated.action?num=${dto.num}&pageNum=${pageNum}'"/>
		<input type="button" value=" 삭제 " class="btn2" 
		onclick="javascript:location.href='<%=cp%>/deleted.action?num=${dto.num}&pageNum=${pageNum}'"/>
		</div>		
		<div id="rightFooter">
		<input type="button" value=" 리스트 " class="btn2" 
		onclick="javascript:location.href='<%=cp%>/list.action?${params}'"/>
		</div>	
		
	</div>
</div>

</body>
</html>


 

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>Insert title here</title>

<link rel="stylesheet" href="/springweb/resources/css/style.css" type="text/css"/>
<link rel="stylesheet" href="/springweb/resources/css/list.css" type="text/css"/>

<script type="text/javascript">

	function sendIt(){
		
		var f = document.searchForm;
		
		f.action = "<%=cp%>/list.action";
		f.submit();		
	}
	
</script>

</head>
<body>

<div id="bbsList">
	<div id="bbsList_title">
	게 시 판(Spring)
	</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%>/created.action';"/>		
		</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>

 

updated.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>게 시 판</title>

<link rel="stylesheet" href="/springweb/resources/css/style.css" type="text/css"/>
<link rel="stylesheet" href="/springweb/resources/css/created.css" type="text/css"/>

<script type="text/javascript" src="/springweb/resources/js/util.js"></script>

<script type="text/javascript">

	function sendIt(){
		
		f = document.myForm;
		
		str = f.subject.value;
		str = str.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;
		}		
		/*
		if(!isValidKorean(str)){			
			alert("\n이름을 정확히 입력하세요.");
			f.name.focus();
			return;
		}
		*/
		f.name.value = str;
		
		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%>/updated_ok.action";
		f.submit();
		
	}

</script>

</head>
<body>

<div id="bbs">
	<div id="bbs_title">
	게 시 판(Spring)	
	</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"/>
				</dd>							
			</dl>		
		</div>	
	
	</div>	
	
	<div id="bbsCreated_footer">
	
	<input type="hidden" name="num" value="${dto.num }"/>
	<input type="hidden" name="pageNum" value="${pageNum }"/>
	
	<input type="button" value=" 수정하기 " class="btn2" 
	onclick="sendIt();"/>
	
	<input type="button" value=" 수정취소 " class="btn2" 
	onclick="javascript:location.href='<%=cp%>/list.action';"/>	
	</div>
	
	</form>
	
</div>

</body>
</html>

 

 

5. BoardController

 

@Autowired 
Setter 메서드, 생성자 메서드 또는 필드(프로퍼티)에 직접 설정 해서  
자동으로 의존성 주입이 수행되도록 구성

 

@Qualifier  
@Autowired와 함께 사용되어서 자동 의존성 주입이 수행될 대상 Bean을 구체적으로 설정

 

- Servlet 방식으로 게시판을 만들었을 때와의 차이점 : ModelAndView 이용 ,

form양식의 input box 값들은 DTO 객체에 내가 dto.setName~ 하지 않아도 알아서 전달되므로 그에 대한 코드 줄음 

package com.jdbc.springweb;

import java.io.UnsupportedEncodingException;
import java.net.URLDecoder;
import java.net.URLEncoder;
import java.util.List;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.servlet.ModelAndView;

import com.jdbc.dao.BoardDAO2;
import com.jdbc.dto.BoardDTO;
import com.jdbc.util.MyUtil;

@Controller
public class BoardController {
	
	@Autowired
	@Qualifier("boardDAO2") // setter 어노테이션 , Spring DAO 방식 객체 활용
	BoardDAO2 dao;
	
	@Autowired
	MyUtil myUtil;
	//주의 ) 무조건 의존성주입을 다 시키는건 아님
	//MyUtil은 bean객체 어노테이션으로 생성해서 그냥 갖다쓰면됨
	
	@RequestMapping(value="/", method=RequestMethod.GET)
	public String home() {
		
		return "index";
	}
	
	/*
	@RequestMapping(value="/created.action", 
			method= {RequestMethod.GET, RequestMethod.POST})
	public String created(HttpServletRequest request,
			HttpServletResponse response) { 
		
		return "bbs/created";
		
	}*/
	
	// Spring에서 메소드 명은 전혀 중요치 않음. 그냥 구분용
	@RequestMapping(value="/created.action", 
			method= {RequestMethod.GET, RequestMethod.POST})
	public ModelAndView created() { 
		
		ModelAndView mav = new ModelAndView();
		mav.setViewName("bbs/created"); 
		//    생략:  /WEB-INF/views/bbs/created.jsp
		
		return mav;		
	}
	
	@RequestMapping(value="/created_ok.action", 
			method= {RequestMethod.GET, RequestMethod.POST})
	public String created(HttpServletRequest request,
			HttpServletResponse response,  // 안쓰더라도 req,res는  항상 띄워놓기
			BoardDTO dto) { 
		
		int maxNum = dao.getMaxNum();
		dto.setNum(maxNum + 1);

	/*	(Servlet 방식과의 차이점)	
        DTO에 담겨있으니까 얘넨 안써줘도 됨 
  		dto.setName(req.getParameter("name"));
		dto.setSubject(req.getParameter("subject"));
		dto.setEmail(req.getParameter("email"));
		dto.setPwd(req.getParameter("pwd"));
		dto.setContent(req.getParameter("content"));*/
		
		dto.setIpAddr(request.getRemoteAddr());
		
		dao.insertData(dto); 
		// hitcount,count는 sql문에서 넣는것임
		
		return "redirect:/list.action";
		
	}
	
	
	@RequestMapping(value="/list.action", 
			method= {RequestMethod.GET, RequestMethod.POST})
	public String list(HttpServletRequest request,
			HttpServletResponse response) throws UnsupportedEncodingException { 
		
		String cp = request.getContextPath();
		
		String pageNum = request.getParameter("pageNum");
		int currentPage = 1;
		
		if(pageNum != null)
			currentPage = Integer.parseInt(pageNum);
		
		String searchKey = request.getParameter("searchKey");
		String searchValue = request.getParameter("searchValue");
		
		if(searchKey == null){
			
			searchKey = "subject";
			searchValue = "";
			
		}else{
			
			if(request.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.getList(start, end, searchKey, searchValue);
		
		//페이징 처리
		String param = "";
		if(!searchValue.equals("")){
			param = "searchKey=" + searchKey;
			param+= "&searchValue=" 
				+ URLEncoder.encode(searchValue, "UTF-8");
		}
		
		String listUrl = cp + "/list.action";
		if(!param.equals("")){
			listUrl = listUrl + "?" + param;				
		}
		
		String pageIndexList =
			myUtil.pageIndexList(currentPage, totalPage, listUrl);
		
		//글보기 주소 정리
		String articleUrl = 
			cp + "/article.action?pageNum=" + currentPage;
			
		if(!param.equals(""))
			articleUrl = articleUrl + "&" + param;
		
		//포워딩 될 페이지에 데이터를 넘긴다
		request.setAttribute("lists", lists);
		request.setAttribute("pageIndexList",pageIndexList);
		request.setAttribute("dataCount",dataCount);
		request.setAttribute("articleUrl",articleUrl);
		
		return "bbs/list";
		
	}
	
	@RequestMapping(value="/article.action", 
			method= {RequestMethod.GET, RequestMethod.POST})
	public ModelAndView article(HttpServletRequest request,
		HttpServletResponse response) throws UnsupportedEncodingException { 
	
		String cp = request.getContextPath();
		//주의) cp를 바깥에다 쓰면 안됨 request로부터 얻어내는것이기 떄문
		
		int num = Integer.parseInt(request.getParameter("num"));
		String pageNum = request.getParameter("pageNum");
		
		String searchKey = request.getParameter("searchKey");
		String searchValue = request.getParameter("searchValue");
		
		if(searchKey != null)
			searchValue = URLDecoder.decode(searchValue, "UTF-8");
		
		//조회수 증가
		dao.updateHitCount(num);
		
		BoardDTO dto = dao.getReadData(num);
		
		int lineSu = dto.getContent().split("\n").length;
		
		dto.setContent(dto.getContent().replaceAll("\n", "<br/>"));
		
		String param = "pageNum=" + pageNum;
		if(searchKey!=null){
			param += "&searchKey=" + searchKey;
			param += "&searchValue=" 
				+ URLEncoder.encode(searchValue, "UTF-8");
		}
		
		/*
		(Servlet 방식과의 차이점)
		request.setAttribute("dto", dto);
		request.setAttribute("params",param);
		request.setAttribute("lineSu",lineSu);
		request.setAttribute("pageNum",pageNum);	
		
			return "bbs/article";
		*/
		
		ModelAndView mav = new ModelAndView();
		
		mav.setViewName("bbs/article");
		
		mav.addObject("dto", dto);
		mav.addObject("params", param);
		mav.addObject("lineSu",lineSu);
		mav.addObject("pageNum",pageNum);
		
		return mav; 
		
	
	}
	
	
	@RequestMapping(value="/updated.action", 
			method= {RequestMethod.GET, RequestMethod.POST})
	public String updated(HttpServletRequest request,
			HttpServletResponse response) throws UnsupportedEncodingException { 
	

		int num = Integer.parseInt(request.getParameter("num"));
		String pageNum = request.getParameter("pageNum");
		
		BoardDTO dto = dao.getReadData(num);
		
		request.setAttribute("dto", dto);
		request.setAttribute("pageNum", pageNum);
		
		return "bbs/updated";		
		
	}
	
	
	
	@RequestMapping(value="/updated_ok.action", 
			method= {RequestMethod.GET, RequestMethod.POST})
	public String updated_ok(HttpServletRequest request,
			HttpServletResponse response,BoardDTO dto) throws UnsupportedEncodingException { 
	
		String pageNum = request.getParameter("pageNum");
		
		dao.updateData(dto);
		
		return "redirect:/list.action?pageNum=" + pageNum;
		
	}
	
	
	
	
	
	@RequestMapping(value="/deleted.action", 
			method= {RequestMethod.GET, RequestMethod.POST})
	public String deleted(HttpServletRequest request,
			HttpServletResponse response) throws UnsupportedEncodingException { 	
		
		String pageNum = request.getParameter("pageNum");
		int num =Integer.parseInt(request.getParameter("num"));
		
		dao.deleteData(num);
		
		return "redirect:/list.action?pageNum=" + pageNum;
		
	}
}