본문 바로가기
mybatis

스프링부트 MyBatis를 이용하여 MySQL 연동 및 동적쿼리

by khds 2022. 2. 25.

개발자들은 데이터 베이스에 데이터를 유지하기 위해 JDBC를 이용하여 데이터베이스에 접근하였다. JDBC의 복잡함을 단순하게 하게 위해 Persistence FrameWork를 사용했는데 ORM 프레임워크와 SQL 매퍼이다.

 

 

ORM 프레임워크는 SQL 코드를 직접 작성하지 않고 자바에서 객체지향적인 방식으로 데이터를 객체로 다루면 이를 관계형 데이터베이스에서 작업할 때 SQL로 변환하여 연동을 할 수 있도록 하는 것이다.  즉 SQL을 직접 작성할 필요가 없는 것이다. 데이터베이스에 종속성이 약해서 바뀌더라도 바로바로 적용 가능하다. 대표적으로는 Hibernate가 있고 이에 대한 표준 기술 명세가 JPA이다.

 

 

MyBatis는 ORM 프레임워크라고 말하지는 않고 SQL 매퍼라고 한다. 객체와 관계형 데이터베이스의 데이터를 개발자가 작성한 SQL로 매핑시켜주는 프레임워크이다. 개발자가 SQL을 직접 작성해야 하며 SQL문을 실행하고 얻은 데이터를 객체로 매핑시켜준다.

 

 

그럼 이제 MyBatis를 스프링 부트 프로젝트에 적용시켜 보자. 

 

Gradle에선 아래와 같이 설정한다.

 

implementation 'org.mybatis.spring.boot:mybatis-spring-boot-starter'

 

 

Maven에선 아래와 같이 설정한다. 

 

<dependency>
            <groupId>org.mybatis.spring.boot</groupId>
            <artifactId>mybatis-spring-boot-starter</artifactId>
            <version>2.1.4</version>
</dependency>

 

 

매번 DB Connection 을 하는 것은 좋지 않기 때문에 커넥션 풀을 설정해서 미리 연결을 통해 맺은 객체들을 풀에 저장해 놓았다가 요청이 오면 connection을 해주고, 처리가 다 끝나면 다시 반납해줘서 pool에 저장하는 방식이다. 설정하는 방식은 DataSource를 설정해야 하지만 스프링 부트에서는 aaplication.properties 혹은 .yml에서 설정이 가능하다.

아래와 같이 application.yml 에 기본적인 mysql 설정을 해준다. 

 

spring:
  datasource:
    driver-class-name: com.mysql.cj.jdbc.Driver
    url: jdbc:mysql://localhost:3306/calendar?serverTimezone=Asia/Seoul
    username: calendar
    password: calendar

 

 

mysql 설정은  https://khdscor.tistory.com/35?category=977203 를 참고하길 바란다.

 

스프링부트 With JPA - mysql 연동

이 글에서는 간단하게 스프링 부트에서 mysql과 연동하는 방식을 봐보겠다. mysql은 https://dev.mysql.com/downloads/workbench/ MySQL :: Download MySQL Workbench Select Operating System: Select Operating..

khdscor.tistory.com

 

 

1. @MapperScan

MyBatis의 가장 핵심적인 객체는 SQLSession와 SQLSessionFactory 객체다. SQLSessionFactory는 내부적으로 SQLSession을 생성해내는데 이 SQLSession을 통해서 Connection을 생성하거나 원하는 SQL을 전달하고, 결과를 리턴 받는 구조로 작성하게 된다. 스프링은 SQLSession와 SQLSessionFactory 객체를 생성하여 빈으로 등록해야 하지만 스프링 부트에서는 메인 애플리케이션에 @MapperScan을 사용하면 스프링 부트가 @Mapper가 붙은 MyBatis 매퍼를 스캔하여 빈으로 등록할 수 있도록 한다.

 

아래와 같이 스프링 부트 메인 애플리케이션 클래스 @MapperScan을 붙이고 mapper 패키지 경로를 입력한다.

 

@MapperScan
@SpringBootApplication
public class CalenderApplication {
    public static void main(String[] args) {
        SpringApplication.run(CalenderApplication.class, args);
    }
}

 

 

2. Mapper 생성

Mapper는 어노테이션을 이용해서 자바 파일에 구현하는 방법과 xml파일에 구현하는 방법이 있다. 

먼저 자바파일에 구현하는 것은 아래와 같다.

 

화면과 같이 mapper 패키지를 만들고 ArticleMapper 인터페이스를 만들었다. 여기서 중요한 점이 인터페이스가 Mapper라는 것을 인식할 수 있게 @Mapper을 꼭 붙여주어야 한다. 그래야 @MapperScan에서 찾을 수 있다. 만약 스프링 부트가 아닌 스프링을 사용한다면 root-context.xml 파일에 설정을 해주어야 한다.

 

@Mapper
public interface ArticleMapper {

    @Select("SELECT * FROM article WHERE id = #{id}")
    Article findById(Long id);
}

 

위와 같이 findById를 만들었고 이를 사용하는 코드는 아래와 같다. 

 

    @Transactional
    public void write(Long articleId, Long userId, String content) {
        User user = userRepository.findById(userId)
            .orElseThrow(() -> new NotExistsUserException("해당되는 유저가 존재하지 않습니다."));
        /*Article article = articleRepository.findById(articleId)
            .orElseThrow(() -> new NotExistsArticleException("해당되는 게시글이 존재하지 않습니다."));*/
        Article article = articleMapper.findById(articleId);
        if(article == null)
            throw new NotExistsArticleException("해당되는 게시글이 존재하지 않습니다.");
        
        commentRepository.save(Comment.builder()
            .content(content)
            .user(user)
            .article(article)
            .build());
    }
}

 

 

위 wirte는 user와 article를 가지고 comment를 만들어서 저장하는 코드이다. 본래는 JPA를 사용하였지만 Article를 가져오는 과정은 MyBatis를 사용한 것을 알 수 있다. 만약 articleId에 해당되는 article 이 없으면 null을 리턴한다. 

 

 

그다음 xml을 이용하는 방법을 살펴보겠다. 아래와 같이 resource 안에 패키지와 xml 파일을 만든다. 

 

 

그리고 yml파일에 아래와 같이 xml 파일의 경로를 설정한다. 

 

mybatis:
  mapper-locations: mapper/**/*.xml

 

 

그리고 만들었던 ArticleMapper에 메서드를 추가한다. 

 

 

 

이제 xml 파일에 findById2에 대한 내용을 작성하면 된다.  findById와 똑같은 기능이며 내용은 아래와 같다.

 

<?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="calender.calender.mapper.ArticleMapper">
  <select id="findById2" resultType="calender.calender.domain.Article">
    SELECT * FROM article WHERE id = #{id}
  </select>
</mapper>

 

 

위와 같이 작성하면 findById2를 호출하면 findById와 똑같이 작동할 것이다. 

 

이렇게 두 가지 방식이 있는데 각각 장단점을 가지고 있다. interface파일에 어노테이션을 통해 구현하는 방식은 코드가 매우 간결하지만 복잡한 쿼리문을 짜야할 때에는 이 방식이 좋지는 않다. xml파일에 구현하는 방식은 코드가 길긴 하지만 복잡한 쿼리문을 짤 때 더 유용하다. 그렇기에 상황에 맞게 작성하면 될 것이다. 

 

 

위에 예시에서는 간단하게 select만을 확인하였고 그 밖에 CRUD 기능도 비슷하게 구현해주면 된다. insert는 void 타입으로, delete는 int 타입인데 삭제하기 위한 데이터가 존재하면 1을, 존재하지 않으면 0을 출력한다. update도 int 타입으로 몇 개의 데이터가 수정됐는지를 확인할 수 있다. 

 

아래는 insert를 사용했을 때의 예시이다. 

 

@Insert("INSERT INTO  comment(content, created_date, article_id, user_id) VALUES (#{content}, #{created_date}, #{article_id}, #{user_id})")
void createComment(String content, Long article_id, Long user_id, Date created_date);

 

 

 

참고

https://azurealstn.tistory.com/83

 

Spring Boot + gradle + Oracle 11g + MyBatis 연동

Spring Boot + gradle + Oracle 11g + MyBatis 연동 먼저 SQL Developer 또는 CMD(sqlplus -> 환경변수 설정)로 System 계정으로 들어가 유저를 생성합니다. 모든 권한 부여도 해주고, 기본적으로 DB 포트번호가 8..

azurealstn.tistory.com

 

https://dongjuppp.tistory.com/78

 

Spring Boot + Mybatis

org.mybatis.spring.boot mybatis-spring-boot-starter 2.1.4 이글은 스프링 부트에서 마이바티스를 사용하는 방법을 설명한 글이다. 기존의 스프링 프레임워크와 마이바티스는 xml기반의 설정인데 스프링 부트

dongjuppp.tistory.com

 

https://firework-ham.tistory.com/110

 

[DB] ORM, SQL Mapper 이란?

ORM과 SQL Mapper의 개념을 정리하기전 영속성(Persistence)에 대해 먼저 정리해보겠습니다. 영속성(Persistence) 영속성이란 프로그램이 종료되어도 데이터가 사라지지 않는 특성을 말한다. 영속성을 갖

firework-ham.tistory.com

 

https://devlog-wjdrbs96.tistory.com/200

 

[Spring Boot] 스프링부트에서 Mybatis 사용하기

먼저 Mybatis를 얘기하기 전에 JAVA의 ORM이 무엇이 있는지 어떤 것인지에 대해서 정리해보자. ORM(Object Relational Mapping)이란? ORM에서 Object는 객체지향 언어의 객체를 의미한다. Relational은 관계형 데..

devlog-wjdrbs96.tistory.com

 

https://lotuus.tistory.com/75

 

[MyBatis] 동작원리, 사용방법 정리

목차 MyBatis 등장배경 [JDBC] 사용방법 JDBC : JAVA DataBase Connectivity 기존 자바에서는 DB를 조작하기 위해서 JDBC API를 사용했다. JDBC는 데이터베이스 종류에 상관없이 JDBC만 알면 어떤 데이터베이스를

lotuus.tistory.com

 

https://mybatis.org/mybatis-3/ko/dynamic-sql.html

 

MyBatis – 마이바티스 3 | 동적 SQL

동적 SQL 마이바티스의 가장 강력한 기능 중 하나는 동적 SQL을 처리하는 방법이다. JDBC나 다른 유사한 프레임워크를 사용해본 경험이 있다면 동적으로 SQL 을 구성하는 것이 얼마나 힘든 작업인지

mybatis.org

 

코드로 배우는 스프링 웹 프로젝트 - 구멍가게 코딩단