Ch. 04 Spring - MyBatis
2023. 1. 21. 21:43
1. MyBatis
MyBatis란?
- SQL Mapping Framework로 자바코드와 SQL을 맵핑해준다. (XML을 별도 SQL로 분리 )
- 자바 코드로부터 SQL 문을 분리해서 관리
- 매개변수 설정과 쿼리 결과를 읽어오는 코드를 제거
- 작성할 코드를 줄어서 생산성 향상 & 유지 보수 편리
<SqlSessionFactoryBean 과 SqlSessionTemplate>
- SqlSessionFactory : SqlSession을 생성해서 제공 (인터페이스)
- SqlSession : SQL 명령을 수행하는데 필요한 메서드를 제공 (인터페이스)
- SqlSessionFacotryBean : SqlSessionFactory를 Spring에서 사용하기 위한 빈 (위 인터페이스 구현)
- SqlSessionTemplate : SQL명을 수행하는데 필요한 메서드를 제공 thread-safe (위 인터페이스 구현)
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource"/>
<property name="configLocation" value="classpath:mybatis-config.xml"/>
<!--property name="mapperLocations" value="classpath:mapper/*Mapper.xml"/-->
</bean>
<bean id="sqlSession" class="org.mybatis.spring.SqlSessionTemplate">
<constructor-arg ref="sqlSessionFactory"/>
</bean>
//*Mapper.xml : SQL XML 문서
[참고] - thread-safe
- 예를 들어 thread-safe이므로 BoardDao와 UserDao가 SqlSessionTemplate를 공유 가능하다
- 멀티쓰레드에 안전하다는 뜻, 여러 쓰레드가 동시에 접근해도 괜찮다
SqlSession의 주요 메서드
<typeAliases>
- parameterType이 너무 길어서 별명 사용
- alias는 대소문자 구별 안함
<mybatis-config.xml>
<typeAliases> <typeAlias alias="BoardDto" type="com.fastcampus.ch4.domain.BoardDto"/> </typeAliases>
<BoardDao의 작성> - 예시
Mapper XML의 parameterType으로 입력받아서 resultType으로 반환하는 것
1. DB 테이블 생성
2. Mapper XML & DTO 작성
3. DAO 인터페이스 작성
4. DAO 인터페이스 구현 & 테스트
예시) BoardDaoImpl.java
@Repository
public class BoardDaoImpl implements BoardDao {
@Autowired
SqlSession session;
String namespace= "com.fastcampus.ch4.dao.BoardMapper.";
//이 메소드를 호출하면 boardMapper의 sql문을 호출하고
// 결과를 반환 받는다
@Override
public BoardDto select(int bno) throws Exception{
return session.selectOne(namespace + "select", bno);
}
}
예시) BoardDaoImplTest.java
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = {"file:src/main/webapp/WEB-INF/spring/root-context.xml"})
public class BoardDaoImplTest {
@Autowired
BoardDao boardDao;
@Test
public void select() throws Exception{
assertTrue(boardDao != null);
System.out.println("boardDao = " + boardDao);
boardDao.select(1);
BoardDto boardDto = boardDao.select(1);
System.out.println("boardDto = " + boardDto);
assertTrue(boardDto.getBno().equals(1));
}
}
DTO(Data Transfer Object)란?
- 계층 간의 데이터를 주고 받기 위해 사용되는 객체
- 글을 읽을 때는 테이블의 데이터를 DTO에 담아서 가져오고, 글을 쓸 때는 DTO 객체에 값을 채워서 DB의 table에 저장함
- @Repository에서는 예외처리 안하고 무조건 @Service에 보고를 함
- @Service에서 처리 안되는 건 @Controller로 보고 (양쪽에서 처리도 가능)
예시) BoardDto.java
public class BoardDto {
// table column
private Integer bno;
private String title;
private String content;
private String writer;
private int view_cnt;
private int comment_cnt;
private Date reg_date;
...
// equals(), hashCode(), getter and setter
// constructor, toString
[참고]
- null이 int로 들어가면 변환에러, null이 Integer로 들어가면 OK (처리는 필요하지만 에러는 안남)
Mapper.xml - 예시
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.fastcampus.ch4.dao.BoardMapper">
<delete id="delete" parameterType="map">
DELETE FROM board WHERE bno = #{bno} and writer = #{writer}
</delete>
<insert id="insert" parameterType="BoardDto">
INSERT INTO board
(title, content, writer)
VALUES
(#{title}, #{content}, #{writer})
</insert>
<sql id="selectFromBoard">
SELECT bno, title, content, writer, view_cnt, comment_cnt, reg_date
FROM board
</sql>
<select id="select" parameterType="int" resultType="BoardDto">
<include refid="selectFromBoard"/>
WHERE bno = #{bno}
</select>
<update id="update" parameterType="BoardDto">
UPDATE board
SET title = #{title}
, content = #{content}
, up_date = now()
WHERE bno = #{bno}
</update>
<update id="increaseViewCnt" parameterType="int">
UPDATE board
SET view_cnt = view_cnt + 1
WHERE bno = #{bno}
</update>
</mapper>
#{}와 ${}의 차이
XML내의 특수 문자 처리
- XML 내의 특수 문자 (<,>,&, ...)는 < >로 변환 필요
- 특수문자가 포함된 쿼리를 <![CDATA[ 와 ]]>로 감싼다
<기능 구현 순서>
1. DB테이블 생성
2. Mapper XML 작성 (SQL) - myBatis
3. DAO 작성 테스트 (@Repository)
4. Service 작성 테스트 (@Service)
5. 컨트롤러 작성 테스트 (@Controller)
6. 뷰(UI) 작성 테스트
'Spring > 스프링의 정석' 카테고리의 다른 글
Ch. 04 REST API와 Ajax (0) | 2023.01.27 |
---|---|
Ch. 03 Spring 서비스 계층의 분리와 @Transactional (0) | 2023.01.14 |
Ch. 03 Spring Transaction, AOP (0) | 2023.01.14 |
Ch. 03 Spring DB연결, DAO (0) | 2023.01.13 |
Ch. 03 Spring DI (0) | 2023.01.12 |