본문 바로가기

Spring

[Spring] JDBC Template 사용

반응형

템플릿 메서드 패턴 

반복적인 로직을 가지는 부분을 캡슐화해서 사용
코딩 순서가 정형화된 기술을 재사용하기 용이하게 모듈화해놓은것 

  • Template 패턴의 장점
    • 코드 중복 감소
    • 자식 클래스의 역할을 감소시키면서 핵심로직 관리 용이
    • 객체 추가 및 확장을 쉽게 가능
    • 재사용성 증가
  • Template 패턴의 단점
    • 추상 메소드가 너무 많으면 복잡성 증가
    • 추상 클래스와 구현 클래스간의 관계 복잡도가 증가

 

JDBC Template

  • 스프링의 가장 기본적인 Data Access 템플릿으로 쿼리 기반으로 데이터 베이스의 접근 가능
  • 모든 영속성 프래임워크는 내부적으로 JDBC API를 이용
  • DAO 계층에서 Jdbc Template API를 사용
  • Data Source
    • DB Server와 연결 시키는 연결 팩토리
    • JDBC의 일부분
    • Connection 의 정보를 가지고 있고 Bean 으로 등록하여 인자를 넘겨줌 
    • DB Connection Pooling 기능을 가지고 있음
    • 기본적으로 BasicDataSource를 사용

JDBC Template 적용 방법 

 

1. 라이브러리 추가 

pom.xml 에 추가한 뒤 Maven Dependencies에 잘 적용되었는지 확인 

<!-- DBCP -->
      <dependency>
         <groupId>commons-dbcp</groupId>
         <artifactId>commons-dbcp</artifactId>
         <version>1.4</version>
      </dependency>


2. JdbcTemplate에서 활용할 DataSource 추가 

 

dbcTemplate에서 활용할  DataSource를 컨테이너가 생성할 수 있도록 객체화를 해주어야하는데   

이는 <bean>을 통해서 처리함 

기존 Util 파일의 정보들은 setter 인젝션 사용하여 DI 를 해줌 

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
   xmlns:p="http://www.springframework.org/schema/p"
   xmlns:context="http://www.springframework.org/schema/context"
   xmlns:aop="http://www.springframework.org/schema/aop"
   xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
      http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-4.2.xsd
      http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-4.2.xsd">

     <context:component-scan base-package="com.kim.biz" />
   
   <!-- DataSource 설정하기 -->
   <!-- string값을 넣어주기 때문에 ref가 아닌 value로 사용 -->
	<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close">
		<property name="driverClassName" value="oracle.jdbc.driver.OracleDriver"/>		
		<property name="url" value="jdbc:oracle:thin:@localhost:1521:xe"/>		
		<property name="username" value="kim"/>		
		<property name="password" value="1234"/>		
	</bean>
	
	<!-- Spring JDBC 설정하기 -->
	<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
		<property name="dataSource" ref="dataSource"/>
	</bean>	
	
</beans>

만약 Spring JDBC 설정하기 부분에서 오류가 난다면 

pom.xml에 하기 코드를 추가하면 해결

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

3. DAO 내용 변경 

 

기존 BoardDAO내용을 JdbcTemplate 적용할 BoardDAO2 파일 생성 

 

스프링이 관리하는 Bean을 자동으로 주입해주는 어노테이션인 @Autowired를 사용하여 

JdbcTemplate 의 멤버변수가 DI되도록 함

 

해당 클래스가 DAO라는걸 알리기 위해서 @Repository라고 기입 - 기존 BoardDAO 파일의 @Repository는 삭제 

package com.kim.biz.board.impl;

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

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.RowMapper;
import org.springframework.stereotype.Repository;

import com.kim.biz.board.BoardVO;

@Repository("boardDAO")
public class BoardDAO2 {

   @Autowired
   private JdbcTemplate jdbcTemplate;
   
   final String sql_selectOne="SELECT * FROM BOARD WHERE BID=?";
   final String sql_selectAll="SELECT * FROM BOARD ORDER BY BID DESC";
   final String sql_insert="INSERT INTO BOARD(BID,TITLE,WRITER,CONTENT) VALUES((SELECT NVL(MAX(BID),0)+1 FROM BOARD),?,?,?)";
   final String sql_update="UPDATE BOARD SET TITLE=?,CONTENT=? WHERE BID=?";
   final String sql_delete="DELETE BOARD WHERE BID=?";
   
   void insertBoard(BoardVO vo) {
      jdbcTemplate.update(sql_insert,vo.getTitle(),vo.getWriter(),vo.getContent());
   }
   void updateBoard(BoardVO vo) {
      jdbcTemplate.update(sql_update,vo.getTitle(),vo.getContent(),vo.getBid());
   }
   void deleteBoard(BoardVO vo) {
      jdbcTemplate.update(sql_delete,vo.getBid());
   }
   BoardVO selectOneBoard(BoardVO vo) {
      Object[] args= {vo.getBid()};
      return jdbcTemplate.queryForObject(sql_selectOne,args,new BoardRowMapper());
   }
   List<BoardVO> selectAllBoard(BoardVO vo) {
	   System.out.println("★★★★★잘들어갔니?? 확인용★★★★★");
      return jdbcTemplate.query(sql_selectAll,new BoardRowMapper());
   }
}
class BoardRowMapper implements RowMapper<BoardVO>{

   @Override
   public BoardVO mapRow(ResultSet rs, int rowNum) throws SQLException {
      BoardVO data=new BoardVO();
      data.setBid(rs.getInt("BID"));
      data.setContent(rs.getString("CONTENT"));
      data.setTitle(rs.getString("TITLE"));
      data.setWriter(rs.getString("WRITER"));
      data.setCnt(rs.getInt("CNT"));
      data.setRegdate(rs.getString("REGDATE"));
      return data;
   }
   
}

 


JdbcTempate 메서드 

 

update 메서드 - ( INSERT, UPDATE, DELETE 적용) 

int update(String sql, Object args, ...) 
int update(String sql, Object[] args) 

 

queryForObject() 메서드  - (SELECT문으로 객체 하나를 검색할 때 사용하는 메소드

Object queryForObject(String sql, Object args, 매핑정보)

-> resultset과 vo를 매핑할 RowMapper 객체를 반드시 지정해야함
ex) SELECT * FROM 테이블명 WHERE PK=?;

 

List query() 메서드 -  (ELECT문의 실행 결과가 목록일 때 사용하는 메소드)

List query(String sql, Object[] args, 매핑정보) 

-> 검색 결과를 VO 객체에 매핑하려면 RowMapper 객체를 사용함


4. BoardServiceImpl.java의 @Autowired 연결을 BoardDAO2로 수정 

 

package com.kim.biz.board.impl;

import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.kim.biz.board.BoardService;
import com.kim.biz.board.BoardVO;

@Service("boardService")
public class BoardServiceImpl implements BoardService {

	@Autowired
	private BoardDAO2 boardDAO;
	
	@Override
	public void insertBoard(BoardVO vo) {
		boardDAO.insertBoard(vo);
	}

	@Override
	public void updateBoard(BoardVO vo) {
		boardDAO.updateBoard(vo);
	}

	@Override
	public void deleteBoard(BoardVO vo) {
		boardDAO.deleteBoard(vo);
	}

	@Override
	public BoardVO selectOneBoard(BoardVO vo) {
		return boardDAO.selectOneBoard(vo);
	}

	@Override
	public List<BoardVO> selectAllBoard(BoardVO vo) {
		return boardDAO.selectAllBoard(vo);
	}

}

JDBCTemplate을 사용하니 훨씬 더 간결한 코드가 완성되는데 너무 신기하다...

 

 

반응형