도서 API 구현
도서 테이블 생성
CREATE TABLE `books` (
id INT NOT NULL AUTO_INCREMENT,
title VARCHAR(45) NOT NULL,
`format` VARCHAR(45) NOT NULL,
isbn VARCHAR(45) NOT NULL,
summary VARCHAR(500) NULL,
`description` LONGTEXT NULL,
author VARCHAR(45) NOT NULL,
pages INT NOT NULL,
`index` LONGTEXT NULL,
price INT NOT NULL,
pub_date DATE NULL,
PRIMARY KEY (`id`),
UNIQUE INDEX `isbn_UNIQUE` (`isbn` ASC)
);
컬럼명 변경
방금 위에서 만들 테이블에서 format, description, index에는 백팁을 사용한 이유가 무엇을까? 그 이유는 format, description, index는 mysql에서 사용하고 있는 예약어이기 때문이다.
예약어란?
데이터베이스 시스템이 자기만의 특수한 목적을 위해 이미 '찜'해놓은 단어들을 말한다.
MySQL에서 사용하는 예약어
- index
"데이터를 빨리 찾기 위해 색인(Index)을 만들어라"라는 아주 중요한 명령어이다. 그래서 이걸 컬럼명으로 쓰면 DB는 "색인을 만들라는 거야, 아니면 컬럼 이름이라는 거야?"라며 헷갈려서 에러를 낸다. - format
특정 데이터의 형식을 바꾸는 함수 이름으로 예약되어 있다. - description
특정 데이터의 상세 구조를 보여달라는 명령(DESC)과 비슷하여 혼동을 줄 수 있다.
컬럼명 수정
그래서 해당 컬럼명을 바꿔주도록 하겠습니다.
format -> form
description -> detail
index -> contents
ALTER TABLE books CHANGE COLUMN `format` form VARCHAR(45) NOT NULL;
ALTER TABLE books CHANGE COLUMN `description` detail LONGTEXT NULL;
ALTER TABLE books CHANGE COLUMN `index` contents LONGTEXT NULL;
도서 전체 조회 구현
우선 전체 도서 조회 api 구현하고 postman을 통해 확인해보겠습니다.
bookController
export const getAllbooks = (req, res) => {
const sql = `SELECT * FROM books`;
conn.query(sql, (err, results) => {
if (err) {
console.error("도서 전체 조회 요청 DB 에러:", err);
return res.status(StatusCodes.INTERNAL_SERVER_ERROR).json(err);
}
return res.status(StatusCodes.OK).json(results);
});
};
books.js
import express from "express";
import { getAllbooks, getBookById } from "../controller/bookController.js";
const router = express.Router();
router
.get("/", getAllbooks)
export default router;

개별 도서 조회 구현
bookController
export const getBookById = (req, res) => {
const { id } = req.params;
const sql = `SELECT * FROM books WHERE id = ?`;
conn.query(sql, [id], (err, results) => {
if (err) {
console.error("도서 개별 조회 요청 DB 에러:", err);
return res.status(StatusCodes.INTERNAL_SERVER_ERROR).json(err);
}
if (results[0]) {
return res.status(StatusCodes.OK).json(results[0]);
} else {
return res.status(StatusCodes.NOT_FOUND).json({
message: "존재하지 않는 도서입니다.",
});
}
});
};
books.js
router
.get("/", getAllbooks)
.get("/:id", getBookById);
books 테이블에 이미지 컬럼 추가
ALTER TABLE books ADD COLUMN img INT NULL AFTER title;
카테고리별 도서 목록 조회
books 테이블에 category_id 컬럼 추가
ALTER TABLE books ADD COLUMN category_id INT NULL AFTER img;
bookController getAllBooks 수정
export const getAllbooks = (req, res) => {
const { category_id } = req.query;
if (category_id) {
const sql = `SELECT * FROM books WHERE category_id=?`;
conn.query(sql, [caategory_id], (err, results) => {
if (err) {
console.error("카테고리별 조회 요청 DB 에러:", err);
return res.status(StatusCodes.INTERNAL_SERVER_ERROR).json(err);
}
return res.status(StatusCodes.OK).json(results);
});
} else {
const sql = `SELECT * FROM books`;
conn.query(sql, (err, results) => {
if (err) {
console.error("도서 전체 조회 요청 DB 에러:", err);
return res.status(StatusCodes.INTERNAL_SERVER_ERROR).json(err);
}
return res.status(StatusCodes.OK).json(results);
});
}
};
결과

카테고리 API 구현
카테고리 테이블 생성
CREATE TABLE category (
id INT NOT NULL,
name VARCHAR(100) NOT NULL,
PRIMARY KEY(id)
);
데이터 삽입
INSERT INTO category (id, name)
VALUES
(0, '동화'),
(1, '소설'),
(2, '사회');
구현
categoryController
import conn from "../db/mysql_connect.js";
import { StatusCodes } from "http-status-codes";
export const getAllCategory = (req, res) => {
const sql = `SELECT * FROM category`;
conn.query(sql, (err, results) => {
if (err) {
console.error("카테고리 전체 조회 요청 DB 에러:", err);
return res.status(StatusCodes.INTERNAL_SERVER_ERROR).json(err);
}
return res.status(StatusCodes.OK).json(results);
});
};
category.js
import express from "express";
import { getAllCategory } from "../controller/categoryController.js";
const router = express.Router();
router.get("/", getAllCategory);
export default router;
app.js 라우터 추가
import categoryRouter from "./routes/category.js";
app.use("/category", categoryRouter);
결과

'pgms' 카테고리의 다른 글
| [7주차] - [9기] 타입스크립트로 함께하는 웹 풀 사이클 개발(React, Node.js) 10회차 - 31 (0) | 2026.02.24 |
|---|---|
| [7주차] - [9기] 타입스크립트로 함께하는 웹 풀 사이클 개발(React, Node.js) 10회차 - 30 (0) | 2026.02.23 |
| [6주차] - [9기] 타입스크립트로 함께하는 웹 풀 사이클 개발(React, Node.js) 10회차 - 28 (0) | 2026.02.12 |
| [6주차] - [9기] 타입스크립트로 함께하는 웹 풀 사이클 개발(React, Node.js) 10회차 - 27 (0) | 2026.02.11 |
| [6주차] - [9기] 타입스크립트로 함께하는 웹 풀 사이클 개발(React, Node.js) 10회차 - 26 (0) | 2026.02.10 |