오늘 만들 것
이 시리즈를 포함해 많은 개발 가이드 문서가 게시판을 만드는 과정을 설명합니다.
게시판은 데이터의 생성과 호출, 수정, 삭제를 모두 경험해 볼 수 있기 때문입니다.
이렇게 데이터를 다루는 방식들을 줄여서 CRUD(Create, Retrieve, Update, Destory)라고 한 번에 표현하기도 합니다.
이번 글부터 게시판 API 구현을 시작합니다!
보통 데이터 호출을 먼저 진행하지만, 우리는 지난 글에서 데이터 호출을 간략하게 경험했습니다.
그래서 게시글 작성 API를 먼저 제작하고,
오늘 입력한 데이터를 불러오는 API를 다음에 제작해봅니다.
시작하기 전에: MySQL 테이블 생성
Sp-re-ing 시리즈는 Spring Boot가 주제이기 때문에 DB를 다루는 내용은 최소화하려고 합니다.
위 파일을 이용해 테이블을 생성해주세요.
시작
프로젝트를 생성할 때 지난 Lab03와 같이 SQL 의존성을 포함합니다.
DB 연결 정보 등록
/src/main/resources/application.properties
파일에 아래와 같이 접속 정보를 등록합니다.
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.url=jdbc:mysql://localhost:3306/sp_re_ing?serverTimezone=UTC&characterEncoding=UTF-8
spring.datasource.username=jeta
spring.datasource.password=jeta
MyBatis 초기화
lab03과 동일한 방법으로 초기화합니다.
아래와 같이 JavaBean을 생성합니다.
package net.jetalab.spreinglab04;
import org.apache.ibatis.session.SqlSessionFactory;
import org.mybatis.spring.SqlSessionFactoryBean;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.core.io.Resource;
import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
import javax.sql.DataSource;
@SpringBootApplication
public class SpReIngLab04Application {
public static void main(String[] args) {
SpringApplication.run(SpReIngLab04Application.class, args);
}
@Bean
public SqlSessionFactory sqlSessionFactory(DataSource dataSource) throws Exception {
SqlSessionFactoryBean sessionFactory = new SqlSessionFactoryBean();
sessionFactory.setDataSource(dataSource);
Resource[] res = new PathMatchingResourcePatternResolver().getResources("classpath:mappers/*Mapper.xml");
sessionFactory.setMapperLocations(res);
return sessionFactory.getObject();
}
}
DTO 생성
역시 Lombok을 이용해 간편하게 생성할 수 있습니다.
다음 경로에 아래 코드를 작성하여 저장합니다: /src/main/java/YOUR/DOMAIN/ARTIFACT/dto/BoardDTO.java
package net.jetalab.spreinglab04.dto;
import lombok.AllArgsConstructor;
import lombok.NoArgsConstructor;
import lombok.Getter;
import lombok.Setter;
@AllArgsConstructor
@NoArgsConstructor
@Getter
@Setter
public class BoardDTO {
private int seq;
private String title;
private String contents;
private String author;
private String password;
private int reads = 0;
private String deleted = "N";
}
9번째 줄: NoArgsConstructor
는 아무 파라미터도 넘기지 않는 생성자를 만들어줍니다.
18번째 줄 ~ 19번째 줄: reads
와 deleted
에 대해 기본값을 지정했습니다.
DAO 생성
다음 경로에 아래 코드를 작성하여 저장합니다: /src/main/java/YOUR/DOMAIN/ARTIFACT/dao/BoardDAO.java
package net.jetalab.spreinglab04.dao;
import net.jetalab.spreinglab04.dto.BoardDTO;
public interface BoardDAO {
int newBoard(BoardDTO param) throws Exception;
}
6번째 줄: MyBatis의 <insert>
는 INSERT에 성공했을 때 정수 1을 반환합니다.
SQL Mapper 생성
다음 경로에 아래 코드를 작성하여 저장합니다: /src/main/resources/mappers/UserMapper.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="net.jetalab.spreinglab04.dao.BoardDAO">
<insert id="newBoard"
parameterType="net.jetalab.spreinglab04.dto.BoardDTO"
useGeneratedKeys="true"
keyProperty="seq">
INSERT INTO lab04(`title`, `contents`, `author`, `password`)
VALUES (#{title}, #{contents}, #{author}, #{password})
</insert>
</mapper>
7번째 줄: 파라미터로 BoardDTO
객체를 받습니다.
8번째 줄 ~ 9번째 줄: 테이블에 자동 증가가 적용된 열이 있는 경우 INSERT
후 해당 값을 받아올 수 있습니다. useGeneratedKeys
를 true
로 설정하고, keyProperty
에 해당 열의 이름을 적어줍니다.
Controller 생성
POST로 새 글 내용을 받을 Controller를 생성합니다.
다음 경로에 아래 코드를 작성하여 저장합니다: /src/main/java/YOUR/DOMAIN/ARTIFACT/controller/BoardController.java
package net.jetalab.spreinglab04.controller;
import net.jetalab.spreinglab04.dao.BoardDAO;
import net.jetalab.spreinglab04.dto.BoardDTO;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;
@RestController
@EnableAutoConfiguration
@MapperScan(basePackages = "net.jetalab.spreinglab04.dao")
public class BoardController {
@Autowired
private BoardDAO boardDAO;
@RequestMapping(value = "/board", method = RequestMethod.POST)
public BoardDTO postBoard(BoardDTO board) throws Exception {
boardDAO.newBoard(board);
return board;
}
}
20번째 줄: POST 방식으로 요청을 받도록 합니다.
21번째 줄: Body Parameter로 받은 값을 BoardDTO
객체 board
로 받습니다.
22번째 줄: board
객체를 MySQL에 입력합니다. 이 때, INSERT 후 seq
가 갱신됩니다.
23번째 줄: INSERT 한 후의 board
객체를 사용자에게 전송합니다.
디렉토리 구조
모든 파일을 생성하면 지난번과 동일하게 아래와 같은 구조를 가지게 됩니다.
테스트
서버를 실행하고 API를 호출하면 아래와 같이 응답을 받을 수 있습니다.
MySQL에도 올바르게 입력되었습니다.
예제 코드
본 포스트의 예제 코드는 GitHub에 공개되어 있습니다.
https://github.com/jETA-Kor/sp-re-ing/tree/master/lab04