๋ณธ๋ฌธ ๋ฐ”๋กœ๊ฐ€๊ธฐ
๊ฐœ๋ฐœ/Spring

Spring Boot์— MySQL / Mybatis ์—ฐ๊ฒฐํ•˜๊ธฐ

by 1mj 2022. 3. 9.

Spring Boot + MyBatis + MySQL

Spring Boot ํ”„๋กœ์ ํŠธ์—์„œ MyBatis๋ฅผ ์ด์šฉํ•œ MySQL ์—ฐ๋™ ๋ฐฉ๋ฒ•์ด๋‹ค.

* Spring Boot ํ”„๋กœ์ ํŠธ๋ฅผ ์ƒ์„ฑํ•˜๊ณ  ๊ธฐ๋ณธ์ ์ธ ์„ธํŒ…์„ ํ•˜๋Š” ๋ฐฉ๋ฒ•์€ ์—ฌ๊ธฐ์—

 

1. ์˜์กด์„ฑ ์ถ”๊ฐ€

mybatis ๋ฐ mysql์„ ์‚ฌ์šฉํ•˜๊ธฐ ์œ„ํ•ด ํ•ด๋‹น ์˜์กด์„ฑ์„ ์ถ”๊ฐ€ํ•œ๋‹ค.

maven์„ ์‚ฌ์šฉํ•˜๋Š” ํ”„๋กœ์ ํŠธ์˜ ์„ค์ •ํŒŒ์ผ์ธ pom.xml์—์„œ ์˜์กด์„ฑ์„ ์ถ”๊ฐ€ํ•˜๋ฉด ๊ธ€๋กœ๋ฒŒ ์ €์žฅ์†Œ์—์„œ ํ•„์š”ํ•œ ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋ฅผ ๋กœ์ปฌ ์ €์žฅ์†Œ๋กœ ๋‹ค์šด๋กœ๋“œํ•˜๊ณ  ํด๋ž˜์Šค ํŒจ์Šค๋ฅผ ์ง€์ •ํ•˜์—ฌ ํ”„๋กœ์ ํŠธ์—์„œ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋„๋ก ํ•œ๋‹ค. 

 

์•„๋ž˜ ๋งํฌ์˜ MVN Repository์—์„œ ์›ํ•˜๋Š” ์˜์กด์„ฑ์„ ๊ฒ€์ƒ‰ํ•˜์—ฌ ์ถ”๊ฐ€ํ•  ์ˆ˜ ์žˆ๋‹ค. ๋ณดํ†ต ๋ณดํŽธ์ ์ธ ๋ฒ„์ „์ด๋‚˜ ์ตœ์‹  ๋ฒ„์ „์„ ์‚ฌ์šฉํ•œ๋‹ค.

https://mvnrepository.com/artifact/mysql/mysql-connector-java/8.0.28

 

* Duplicating managed version 8.0.28 for mysql-connector-java ๊ฒฝ๊ณ 

์˜์กด์„ฑ์„ ์ถ”๊ฐ€ํ–ˆ๋Š”๋ฐ ์•„๋ž˜์™€ ๊ฐ™์ด ๋…ธ๋ž€์ƒ‰ ๊ฒฝ๊ณ (Duplicating managed version 8.0.28 for mysql-connector-java)๊ฐ€ ๋œจ๋Š” ๊ฒฝ์šฐ๋Š” ์‚ฌ์šฉํ•˜๋ ค๋Š” ๋ฒ„์ „์ด Spring Boot ๋ฒ„์ „๊ณผ ๋งž์ง€ ์•Š์•„์„œ ๋ฐœ์ƒํ•˜๋Š” ๊ฒฝ๊ณ ์ด๋‹ค. ๊ผญ ๊ทธ ๋ฒ„์ „์„ ์‚ฌ์šฉํ•ด์•ผ ํ•˜๋Š” ๊ฒฝ์šฐ๊ฐ€ ์•„๋‹ˆ๋ผ๋ฉด ๋ฒ„์ „์„ ๋งž์ถฐ์ฃผ๋ฉด ๋œ๋‹ค.

 

Spring Boot์—์„œ๋Š” ์˜์กด์„ฑ์„ ์ •์˜ํ•  ๋•Œ ๋ฒ„์ „์„ ๋ช…์‹œํ•˜์ง€ ์•Š์•„๋„ ์•Œ์•„์„œ ์ ์ ˆํ•œ ๋ฒ„์ „์„ ๊ฐ€์ ธ์™€์ฃผ๋Š” ์˜์กด์„ฑ ๊ด€๋ฆฌ ๊ธฐ๋Šฅ์ด ์žˆ๋‹ค.

  • mysql-connector-java: mysql๊ณผ ํ†ต์‹ ํ•  ์ˆ˜ ์žˆ๋„๋ก ํ•˜๋Š” ๋“œ๋ผ์ด๋ฒ„
  • mybatis-spring-boot-starter: spring boot์šฉ mybatis
<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
</dependency>

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

mysql์€ ๊ตณ์ด ๋ฒ„์ „์„ ๋ช…์‹œํ•˜์ง€ ์•Š์•„๋„ ์ž๋™์œผ๋กœ ๋ฒ„์ „์ด ๋งคํ•‘๋˜์ง€๋งŒ mybatis ๊ฐ™์€ ์™ธ๋ถ€ ์˜์กด์„ฑ์€ ๋ฒ„์ „์„ ์ง์ ‘ ์ ์–ด์ฃผ๋Š” ๊ฒƒ์ด ์ข‹๋‹ค.

 

 

2. database ๋ฐ mybatis ์„ธํŒ…

application.properties์— ์•„๋ž˜์™€ ๊ฐ™์ด ์„ค์ •ํ•ด์ค€๋‹ค.

 

๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค ๊ด€๋ จ ์„ค์ •์€ url, ์‚ฌ์šฉ์ž ๊ณ„์ • ์ •๋ณด, ๋“œ๋ผ์ด๋ฒ„ ํด๋ž˜์Šค๋ฅผ ์ ์–ด์ค€๋‹ค.

๋งˆ์ด๋ฐ”ํ‹ฐ์Šค ๊ด€๋ จ ์„ค์ •์€ ๋งคํผ์šฉ ํด๋ž˜์Šค๊ฐ€ ์œ„์น˜ํ•œ ๊ฒฝ๋กœ, xml ํŒŒ์ผ์ด ์œ„์น˜ํ•œ ๊ฒฝ๋กœ๋ฅผ ์ ์–ด ํ•ด๋‹น ๊ฒฝ๋กœ์˜ ํŒŒ์ผ์„ ์ฝ์–ด๋“ค์ด๋„๋ก ํ•˜๋ฉด ๋œ๋‹ค.

# database
spring.datasource.url=jdbc:mysql://localhost:3306/๋ฐ์ดํ„ฐ๋ฒ ์ด์Šค๋ช…?characterEncoding=utf8
spring.datasource.username=๊ณ„์ •ID
spring.datasource.password=๊ณ„์ •PW
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver

# mybatis
mybatis.type-aliases-package=com.plus.tistory.dao
mybatis.mapper-locations=classpath:mybatis/mapper/*.xml

 

3. mybatis-config.xml ํŒŒ์ผ ์ƒ์„ฑ

resources ๋‚ด์— mybatis-config.xml ํŒŒ์ผ์„ ๋งŒ๋“ค๊ณ  ์•„๋ž˜์™€ ๊ฐ™์ด ์ ์–ด์ค€๋‹ค.

๋งŒ์•ฝ ์„ค์ •ํŒŒ์ผ์„ ์ฐพ์ง€ ๋ชปํ•ด ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ•˜๋ฉด application.properties์— mybatis.config=mybatis-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>
    <settings>
        <setting name="mapUnderscoreToCamelCase" value="true" />
        <setting name="callSettersOnNulls" value="true"/>
    </settings>
</configuration>

์—ฌ๊ธฐ๊นŒ์ง€๊ฐ€ ์„ธํŒ…์€ ๋์ด๋‹ค. ์ด์ œ mybatis๋ฅผ ์‚ฌ์šฉํ•˜๊ธฐ ์œ„ํ•ด์„œ๋Š” mvc ํŒจํ„ด์œผ๋กœ db์— ์ ‘๊ทผํ•ด๋ณด์ž.

 

 

4. Controller / Service / Vo / Dao ์ž‘์„ฑ

- Controller

package com.plus.tistory.controller;

import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import com.plus.tistory.service.TestService;
import com.plus.tistory.vo.User;

@RestController
public class TestController {

	@Autowired
	private TestService testService;
	
    @RequestMapping("/")
    public String hello() {
        return "Hello Test Page!";
    }
    
    @GetMapping("/test")
    public List<User> test() {
      return testService.getUserList();
    }
}

 

- Service

package com.plus.tistory.service;

import java.util.List;

import com.plus.tistory.vo.User;

public interface TestService {
    public List<User> getUserList();
}

 

package com.plus.tistory.service;

import java.util.List;

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

import com.plus.tistory.dao.TestMapper;
import com.plus.tistory.vo.User;

@Service
public class TestServiceImpl implements TestService {
    
	@Autowired
	private TestMapper testMapper;

    @Override
    public List<User> getUserList() {
        return testMapper.getUserList();
    }
}

 

- Vo

package com.plus.tistory.vo;

public class User {
    private String name;
    private int age;
    
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public int getAge() {
		return age;
	}
	public void setAge(int age) {
		this.age = age;
	}
}

 

- Dao

@Mapper ์–ด๋…ธํ…Œ์ด์…˜์œผ๋กœ mapper.xml ์„ ์—ฐ๊ฒฐํ•ด์ฃผ๋ฏ€๋กœ ๊ผญ ์ ์–ด์ฃผ์–ด์•ผ ํ•œ๋‹ค.

package com.plus.tistory.dao;

import java.util.List;

import org.apache.ibatis.annotations.Mapper;
import org.springframework.stereotype.Repository;

import com.plus.tistory.vo.User;

@Repository
@Mapper
public interface TestMapper {
    List<User> getUserList();
}

 

<?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.plus.tistory.dao.TestMapper">

  <select id="getUserList" resultType="com.plus.tistory.vo.User">
    SELECT * FROM USER;
  </select>

</mapper>

 

- ํ…Œ์ŠคํŠธ์šฉ ํ…Œ์ด๋ธ” ์ƒ์„ฑ ๋ฐ ๋ฐ์ดํ„ฐ ์‚ฝ์ž…

create table USER (
    name varchar(20),
    age integer
);

insert into USER(name, age) values ('eric', 10);

 

์ด๋ ‡๊ฒŒ ์ž‘์„ฑํ•˜๋ฉด ์—ฐ๋™์€ ๋๋‚œ๋‹ค.

 

* org.apache.ibatis.binding.BindingException: Invalid bound statement (not found) ์˜ค๋ฅ˜

ํ•ด๋‹น ์˜ค๋ฅ˜ ๋ฐœ์ƒ ์‹œ Mapper ์ธํ„ฐํŽ˜์ด์Šค์™€ Mapper xml์—์„œ ์ ์€ id๊ฐ€ ์ผ์น˜ํ•˜๋Š”์ง€ ํ™•์ธํ•ด๋ด์•ผ ํ•œ๋‹ค. ์ผ์น˜ํ•˜๋Š”๋ฐ ์ด์™€ ๊ฐ™์€ ์˜ค๋ฅ˜๊ฐ€ ๋ฐœ์ƒํ•  ๊ฒฝ์šฐ Mapper xml์˜ ์œ„์น˜๋ฅผ ์ง€์ •ํ•ด์ฃผ๋Š” ์„ค์ •ํŒŒ์ผ ๋‚ด mybatis.mapper-locations ์„ค์ • ๊ฒฝ๋กœ๋ฅผ ํ™•์ธํ•ด๋ณด์ž.

 

์„œ๋ฒ„ ๊ธฐ๋™ ํ›„ /test ๊ฒฝ๋กœ๋กœ ์š”์ฒญํ•ด๋ณด๋ฉด ์•„๋ž˜์™€ ๊ฐ™์€ ๊ฒฐ๊ณผ๋ฅผ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋‹ค. RestController๋กœ ๋งŒ๋“ค์–ด๋†จ๊ธฐ ๋•Œ๋ฌธ์— List<User>์˜ ๊ฐ’์„ ๋ฐ˜ํ™˜ํ•œ๋‹ค.

 

 

 

 

 

 

๋Œ“๊ธ€