본문 바로가기
👨‍💻 2. 웹개발_Back end/2-6 Spring

[Spring] 3장 스프링과 MyBatis 연동 - 라이브러리 설정 및 DAO 클래스 구현하는 두 가지 방법 / 스프링과 MyBatis 연동 테스트 / Dynamic SQL 적용

by 달님🌙 2021. 11. 2.
반응형

 

실습 코드 참조

 

moonhy7/SpringFramework: Spring Framework 실습 코드 정리 (github.com)

 

GitHub - moonhy7/SpringFramework: Spring Framework 실습 코드 정리

Spring Framework 실습 코드 정리. Contribute to moonhy7/SpringFramework development by creating an account on GitHub.

github.com

 

 

3.1절 라이브러리 내려받기 ( _075_BoardWeb_Spring_MVC_Mybatis_SqlSessionDaoSupport )

 

1. pom.xml

 

- 스프링과 MyBatis 연동에 필요한 라이브러리들 내려받기

<!-- Mybatis -->	
<dependency>
  <groupId>org.mybatis</groupId>
  <artifactId>mybatis</artifactId>
  <version>3.3.1</version>
</dependency>

<!-- Mybatis Spring -->
<dependency>
  <groupId>org.mybatis</groupId>
  <artifactId>mybatis-spring</artifactId>
  <version>1.2.4</version>
</dependency>

 

2. 라이브러리 확인

 

 

 

3.2절 Mybatis 설정 파일 복사 및 수정

 

1. mappigs 폴더와 sql-map-config.xml 파일 복사 붙여넣기

 

- 스프링과 Mybatis를 연동하려면 Mybatis 메인 환경 설정 파일인 sql-map-config.xml과 SQL 명령어들이 저장되어 있는 Mapper 파일이 필요하다.

- 74번 프로젝트에서 작성한 mappigs 폴더와 sql-map-config.xml 파일을 복사해오기

 

2. sql-map-config.xml 소스 수정

 

- 데이터 소스 관련 설정은 삭제해준다.

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
  PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
  "http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
	<!-- Alias 설정 -->
	<typeAliases>
		<typeAlias type="com.springbook.biz.board.BoardVO" alias="board"></typeAlias>
	</typeAliases>
	
	<!-- Sql Mapper 설정 -->
	<mappers>
		<mapper resource="mappings/board-mapping.xml" />
	</mappers>
	<!-- <mapper resource="mappings/user-mapping.xml" /> -->
</configuration>

 

 

3.3절 스프링 연동 설정

 

- 스프링과 Mybatis를 연동하려면 우선 스프링 설정 파일에 SqlSessionFactoryBean 클래스를 Bean 등록해야한다.

- 그래야 SqlSessionFactoryBean 객체로부터 DB 연동 구현에 사용할 SqlSession 객체를 얻을 수 있다.

- sqlSessionFactory가 SqlSession을 생산하기 위해서는 dataSource와 등록된 mapper 정보가 필요하다.

- 따라서 앞에 등록된 DataSource를 Setter 인젝션으로 참조하고, Sql Mapper가 등록된 sql-map-config.xml도 Setter 인젝션으로 설정해야한다.

- 그래야 bean 등록된 SqlSessionFactoryBean이 SqlSessionFactory 객체를 생성할 수 있다.

<!-- sessionFactory 객체 등록 -->
	<!-- sqlSessionFactory가 SqlSession을 생산하기 위해서는 dataSource와 등록된 mapper정보가 필수 -->
	<bean id="sessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
		<property name="dataSource" ref="dataSource"></property>
		<property name="configLocation" value="classpath:sql-map-config.xml"></property>
	</bean>

 

 

3.4절 DAO 클래스 구현 - 방법1 ( _075_BoardWeb_Spring_MVC_Mybatis_SqlSessionDaoSupport )

 

1. BoardDAOMybatis.java

- 방법 1. SqlSessionDaoSupport 클래스를 상속하여 구현하기

- 스프링 설정 파일에 bean 등록된 SqlSessionFactoryBean 객체를 인자로 받아 부모인 SqlSessionDaoSupport에 setSqlSessionFactory() 메소드로 설정해준다.

- 이렇게 하면 SqlSessionDaoSupport  클래스로부터 상속된 getSqlSession() 메소드를 호출하여 SqlSession 객체를 리턴받을 수 있다.

package com.springbook.biz.board.impl;

import java.util.List;

import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.support.SqlSessionDaoSupport;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

import com.springbook.biz.board.BoardVO;

@Repository
public class BoardDAOMybatis extends SqlSessionDaoSupport {
	@Autowired
	//Spring 컨테이너가 자동으로 메소드를 호출해주고
	//applicationContext파일에 등록된 SqlSessionFactoryBean 객체를 인자로 받아서 메소드를 실행
	public void setSqlSessionFactory(SqlSessionFactory sqlSessionFactory) {
		super.setSqlSessionFactory(sqlSessionFactory);
	}
	
	public void insertBoard(BoardVO vo) {
		System.out.println("====> Mybatis로 insertBoard() 기능 처리");
		getSqlSession().insert("BoardDAO.insertBoard");
	}	
	
	public void updateBoard(BoardVO vo) {
		System.out.println("====> Mybatis로 updateBoard() 기능 처리");
		getSqlSession().update("BoardDAO.updateBoard");
	}	
	
	public void deleteBoard(BoardVO vo) {
		System.out.println("====> Mybatis로 deleteBoard() 기능 처리");
		getSqlSession().delete("BoardDAO.deleteBoard");
	}
	
	public BoardVO getBoard(BoardVO vo) {
		System.out.println("====> Mybatis로 getBoard() 기능 처리");
		return (BoardVO)getSqlSession().selectOne("BoardDAO.getBoard", vo);
	}
	
	public List<BoardVO> getBoardList(BoardVO vo) {
		System.out.println("====> Mybatis로 getBoardList() 기능 처리");
		return getSqlSession().selectList("BoardDAO.getBoardList", vo);
	}
}

 

 

3.5절 DAO 클래스 구현 - 방법2 ( _076_BoardWeb_Spring_MVC_Mybatis_SqlSessionTemplate )

 

1. applicationContext.xml

- 두번째 방법 : SqlSessionTemplate 클래스를 bean 등록하여 사용한다.

- 스프링 설정 파일에서 SqlSessionTemplate 클래스를 SqlSessionFactoryBean 아래에 bean 등록한다.

- SqlSessionTemplate 클래스에는 Setter 메소드가 없어서 Setter 인젝션할 수 없으므로 생성자 메소드를 이용한 Constructor 주입으로 처리할 수 밖에 없다.

- 그러고 나서 DAO 클래스를 구현할 때, SqlSessionTemplate 객체를 @Autowired를 이용하여 의존성 주입 처리하면 SqlSessionTemplate 객체로 DB 연동 로직을 처리할 수 있다.

<!-- SqlSessionTemplate 객체 등록 -->
	<bean class="org.mybatis.spring.SqlSessionTemplate">
		<constructor-arg ref="sessionFactory"></constructor-arg>
	</bean>

 

2. BoardDAOMybatis.java

- SqlSessionTemplate 객체를 @Autowired를 이용하여 의존성 주입 처리하여 SqlSessionTemplate 객체로 DB 연동 로직을 처리할 수 있도록 함

package com.springbook.biz.board.impl;

import java.util.List;

import org.mybatis.spring.SqlSessionTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

import com.springbook.biz.board.BoardVO;

@Repository
public class BoardDAOMybatis {
	@Autowired
	private SqlSessionTemplate mybatis;
	
	public void insertBoard(BoardVO vo) {
		System.out.println("====> Mybatis로 insertBoard() 기능 처리");
		mybatis.insert("BoardDAO.insertBoard");
	}	
	
	public void updateBoard(BoardVO vo) {
		System.out.println("====> Mybatis로 updateBoard() 기능 처리");
		mybatis.update("BoardDAO.updateBoard");
	}	
	
	public void deleteBoard(BoardVO vo) {
		System.out.println("====> Mybatis로 deleteBoard() 기능 처리");
		mybatis.delete("BoardDAO.deleteBoard");
	}
	
	public BoardVO getBoard(BoardVO vo) {
		System.out.println("====> Mybatis로 getBoard() 기능 처리");
		return (BoardVO)mybatis.selectOne("BoardDAO.getBoard", vo);
	}
	
	public List<BoardVO> getBoardList(BoardVO vo) {
		System.out.println("====> Mybatis로 getBoardList() 기능 처리");
		return mybatis.selectList("BoardDAO.getBoardList", vo);
	}
}

 

 

3.6절 MyBatis 연동 테스트

 

1. BoardServiceImpl 클라이언트 프로그램 소스 수정

@Service("boardService")
public class BoardServiceImpl implements BoardService{
	@Autowired
	private BoardDAOMybatis boardDAO;
	...

 

2. 웹 애플리케이션으로 테스트해보기

 

 

3.7절 MyBatis 연동 테스트 ( _077_BoardWeb_Spring_MVC_Mybatis_DynamicSQL )

 

1. Dynamic SQL 적용 전

 

-Mybatis는 SQL의 재사용성과 유연성을 향상하고자 Dynamic SQL을 지원한다.

- 우선 Dynamic SQL의 필요성을 확인하기 위해 Dynamic SQL을 적용하지 않고 검색 기능을 추가해보자

 

1) Board-mapping.xml

- 두 개의 쿼리가 필요함

<!-- Dynamic SQL 적용 전 -->
 	<select id="getBoardList_T" resultType="boardResult">
 		<![CDATA[
 			SELECT * FROM BOARD
 			WHERE TITLE LIKE CONCAT_WS('%', #{searchKeyword}, '%')
 			ORDER BY SEQ DESC
 		]]>
 	</select>
 	
 	<select id="getBoardList_C" resultType="boardResult">
 		<![CDATA[
 			SELECT * FROM BOARD
 			WHERE CONTENT LIKE CONCAT_WS('%', #{searchKeyword}, '%')
 			ORDER BY SEQ DESC
 		]]>
 	</select>

 

2) BoardDAOMybatis.java

- 두 개의 쿼리를 등록했으면 이제 DAO 클래스 getBoardList() 메소드에 검색 조건에 따른 분기 처리 로직을 추가한다.

	public List<BoardVO> getBoardList(BoardVO vo) {
		System.out.println("====> Mybatis로 getBoardList() 기능 처리");		
		
		if(vo.getSearchCondition().equals("TITLE")) {
			return Mybatis.selectList("BoardDAO.getBoardList_T", vo);
		} else if(vo.getSearchCondition().equals("CONTENT")) {
			return Mybatis.selectList("BoardDAO.getBoardList_C", vo);
		}
		return null;
	}

 

3) 단점

- 추가되는 검색 조건에 대해 반복적으로 작성해야한다.

 

2. Dynamic SQL 적용 후

 

- searchCondition 변숫값이 TITLE을 가지고 있으면 제목 검색에 해당하는 조건이 추가되고 CONTENT라는 값을 가지고 있으면 내용 검색에 해당하는 조건이 추가된다.

- 하나의 쿼리로 실행할 수 있다는 장점이 있다.

 <!-- Dynamic SQL 적용 후 -->					
 	<select id="getBoardList" resultMap="boardResult">					
 		SELECT * FROM BOARD 
 		WHERE 1=1
 		<if test="searchCondition == 'TITLE'">
 			AND TITLE LIKE CONCAT_WS('%', #{searchKeyword}, '%')
 		</if>
 		<if test="searchCondition == 'CONTENT'">
 			AND TITLE LIKE CONCAT_WS('%', #{searchKeyword}, '%')
 		</if>	
 		<!-- <if test="title != null">
 			AND 1=1 해주는 이유 : 조건이 많아질 때를 고려해서 where절이 모두 지나가도록 해주려고
 		</if> -->
 			ORDER BY SEQ DESC
 	</select>

 

3. 실행 결과

 

 

 

반응형

댓글