Programmers

[28일차]플레이스홀더 활용, 데이터베이스 테이블 분리

PARKpatchnotes 2025. 10. 20. 17:41

1. 개발 초기 환경 구성을 위한 플레이스홀더(Placeholder) 활용

프로젝트 초기 단계에서는 실제 데이터가 준비되지 않은 경우가 많다. 이때, 디자인 레이아웃과 기능 개발을 원활하게 진행하기 위해 임시 데이터를 채워 넣는 플레이스홀더(Placeholder)를 사용한다. 본 프로젝트에서는 텍스트와 이미지에 각각 로렘 입숨과 픽숨을 활용했다.

가. 로렘 입숨 (Lorem Ipsum)

로렘 입숨은 출판 및 그래픽 디자인 분야에서 의미 없는 텍스트를 채우기 위해 사용하는 표준 더미(dummy) 텍스트다. 개발 과정에서는 다음과 같은 목적으로 사용한다.

  • 콘텐츠 독립적 디자인 검증: 실제 문구가 정해지기 전에 텍스트가 들어갈 공간의 레이아웃, 폰트, 크기, 색상 등이 디자인 시안대로 올바르게 표현되는지 확인할 수 있다.
  • 기능 개발 집중: 개발자는 텍스트 내용이 아닌, 데이터가 화면에 렌더링되는 기능 자체에 집중하여 개발을 진행할 수 있다.

나. 픽숨 포토 (Picsum Photos)

픽숨(https://picsum.photos)은 간단한 URL 요청만으로 지정된 크기의 고품질 이미지를 제공하는 무료 서비스다.

  • 사용법: https://picsum.photos/{가로}/{세로} 형식의 URL을 호출하면 해당 크기의 랜덤 이미지를 반환한다. seed 값을 추가하여 특정 URL이 항상 같은 이미지를 반환하도록 고정할 수도 있다.

    • https://picsum.photos/seed/book1/200/300
  • 활용 목적:

    • 서버 리소스 절약: 개발 단계에서 이미지 파일을 직접 서버에 업로드하고 관리할 필요가 없어 리소스를 절약할 수 있다.
    • 동적 이미지 테스트: 다양한 크기와 비율의 이미지가 UI에 미치는 영향을 손쉽게 테스트할 수 있다.
    • 빠른 프로토타이핑: 데이터베이스에 이미지 URL만 저장하면 되므로, 실제 이미지 데이터 없이도 빠르게 프로토타입을 완성할 수 있다.

2. 데이터베이스 테이블 분리: booksbook_details

초기 설계에서는 도서의 모든 정보를 하나의 books 테이블에 저장했다. 하지만 시스템의 성능과 유지보수성을 고려하여, 이를 booksbook_details 두 개의 테이블로 분리하는 리팩토링을 진행했다.

가. 테이블 분리의 필요성

하나의 큰 테이블을 두 개 이상의 작은 테이블로 나누는 주된 이유는 성능 최적화데이터 관리의 효율성을 높이기 위함이다.

  1. 조회 성능 최적화 및 트래픽 감소 (핵심 이유)

    • 문제 상황: 도서 목록 조회 API는 메인 화면 등 여러 곳에서 빈번하게 호출된다. 이 화면에서는 id, title, author, summary, price, image_url, likes 등 비교적 가벼운 정보만 필요하다.
    • 비효율: 만약 하나의 테이블에 description(상세 설명), table_of_contents(목차)와 같이 용량이 큰 TEXT 타입의 데이터까지 모두 포함되어 있다면, 목록 조회 시 불필요한 대용량 데이터를 함께 읽어오게 된다. 이는 데이터베이스 I/O(입출력) 부하를 증가시키고, 네트워크 트래픽 낭비를 초래하여 API 응답 시간을 느리게 만들고, 시간과 비용을 증가시킨다.
    • 해결: 테이블을 분리함으로써, 목록 조회 시에는 가벼운 정보가 담긴 books 테이블만 조회하고, 사용자가 특정 도서를 클릭하여 상세 정보를 요청할 때만 book_details 테이블을 JOIN하여 조회한다. 이로써 시스템 전반의 성능이 크게 향상된다.
  2. 데이터 정규화 원칙 준수

    • 테이블 분리는 데이터베이스 정규화(Normalization) 원칙과도 맞닿아 있다. 자주 사용되는 데이터와 그렇지 않은 데이터를 분리함으로써 데이터 모델을 더 명확하게 만든다. 이는 데이터의 일관성을 유지하고 중복을 최소화하는 데 도움이 된다. 본 사례는 1:1 관계에서 접근 빈도가 다른 속성을 분리하는 좋은 예시다.
  3. 유지보수성 및 확장성 향상

    • 테이블의 책임과 역할이 명확해진다. books 테이블은 도서의 핵심 식별 정보를, book_details는 부가적인 상세 정보를 담당한다.
    • 향후 '출판사 서평', '저자 인터뷰' 등 새로운 상세 정보 필드를 추가해야 할 경우, 핵심 쿼리에 영향을 주지 않고 book_details 테이블만 수정하면 되므로 시스템 확장성이 좋아진다.

나. 테이블 분리 방법

기존 books 테이블을 booksbook_details로 분리하는 과정은 다음과 같다.

  1. 신규 테이블(book_details) 생성

    • 먼저 상세 정보를 담을 book_details 테이블을 생성한다. 이때 book_id를 기본 키(Primary Key)로 설정하고, 이 키가 books 테이블의 id를 참조하는 외래 키(Foreign Key)가 되도록 하여 1:1 관계를 맺는다.
    CREATE TABLE `book_details` (
      `book_id` INT NOT NULL,
      `description` TEXT NULL,
      `table_of_contents` TEXT NULL,
      `form` VARCHAR(50) NULL,
      `isbn` VARCHAR(13) NOT NULL,
      PRIMARY KEY (`book_id`),
      CONSTRAINT `fk_book_details_books`
        FOREIGN KEY (`book_id`)
        REFERENCES `books` (`id`)
        ON DELETE CASCADE
    );
  2. 데이터 마이그레이션(Migration)

    • 기존 books 테이블에 있던 상세 정보 컬럼의 데이터들을 새로 생성한 book_details 테이블로 복사한다.
    INSERT INTO book_details (book_id, description, table_of_contents, form, isbn)
    SELECT id, description, table_of_contents, form, isbn FROM books;
  3. 기존 테이블(books)에서 컬럼 삭제

    • 데이터가 book_details로 안전하게 이전된 것을 확인한 후, books 테이블에서 더 이상 필요 없는 컬럼들을 삭제한다.
    ALTER TABLE books
    DROP COLUMN description,
    DROP COLUMN table_of_contents,
    DROP COLUMN form,
    DROP COLUMN isbn;

위와 같은 과정을 통해 데이터 손실 없이 안전하게 테이블 구조를 개선하고, 시스템의 성능과 유지보수성을 높일 수 있었다.