백엔드 데이터 인프라 45편 — 데이터베이스 관리 생성·복제·드롭

2026-05-17백엔드 데이터 인프라

백엔드 데이터 인프라 45편. PostgreSQL 데이터베이스 관리 — 생성·복제·드롭·이동·TEMPLATE 표준 풀어쓴 학습 노트.

📚 백엔드 데이터 인프라 · 45편 — 데이터베이스 관리 생성·복제·드롭

이 글은 백엔드 데이터 인프라 시리즈 70편 중 45편이에요. 5편 CREATE DATABASE"기본" 위에 — 운영 깊이.

CREATE DATABASE 운영 옵션

CREATE DATABASE myappdb
    WITH
        OWNER       = app_user
        TEMPLATE    = template0
        ENCODING    = 'UTF8'
        LC_COLLATE  = 'ko_KR.UTF-8'
        LC_CTYPE    = 'ko_KR.UTF-8'
        TABLESPACE  = pg_default
        CONNECTION LIMIT = 100
        IS_TEMPLATE = FALSE
        ALLOW_CONNECTIONS = TRUE;

추가 운영 옵션: - TABLESPACE — 별도 디스크 영역 (대용량·SSD 분리) - IS_TEMPLATE — 다른 DB 가 이걸 템플릿으로 복제 가능 - ALLOW_CONNECTIONS — 접속 차단 (유지보수·복구 중)

TEMPLATE 시스템

PG 의 "DB 만들기" 메커니즘 = 기존 DB 복사.

CREATE DATABASE new_db TEMPLATE original_db;
-- original_db 의 모든 객체·데이터 복사

조건: - 다른 세션이 original_db 에 접속해 있으면 안 됨 - 같은 인코딩·로케일

활용: - 테스트 환경 = 운영 마스킹된 DB → 빠른 복제 - 개발 환경 = 작은 시드 DB → 자주 복제

template0 vs template1

TEMPLATE template1   -- 기본. 다른 사람이 박은 객체 자동 복제 (위험)
TEMPLATE template0   -- 깨끗한 빈 템플릿 (안전, 권장)

운영 = template0 무조건.

DB 복제 — pg_dump·pg_restore

큰 DB 의 복제는 — 다른 도구.

# 덤프
pg_dump -h source.example.com -U postgres -Fc mydb > mydb.dump

# 복원
createdb -h target.example.com -U postgres newdb
pg_restore -h target.example.com -U postgres -d newdb mydb.dump

-Fc = custom format (압축 + 병렬 복원 가능). 46편 백업에서 깊이.

DB 이동·이름 변경

-- 이름 변경 (다른 세션 없어야)
ALTER DATABASE old_name RENAME TO new_name;

-- TABLESPACE 변경
ALTER DATABASE mydb SET TABLESPACE fast_ssd;

-- OWNER 변경
ALTER DATABASE mydb OWNER TO new_owner;

-- CONNECTION LIMIT
ALTER DATABASE mydb CONNECTION LIMIT 200;

ALTER DATABASE SET — DB 단위 설정

-- 이 DB 에 접속하면 자동 적용
ALTER DATABASE mydb SET timezone = 'Asia/Seoul';
ALTER DATABASE mydb SET search_path = app, public;
ALTER DATABASE mydb SET work_mem = '64MB';

DB 별 설정 — 시스템 전체 변경 없이.

다른 사용자 차단

-- 유지보수·복구 중
ALTER DATABASE mydb ALLOW_CONNECTIONS = FALSE;
-- 작업 후
ALTER DATABASE mydb ALLOW_CONNECTIONS = TRUE;

또는 기존 접속 끊기:

SELECT pg_terminate_backend(pid)
FROM pg_stat_activity
WHERE datname = 'mydb' AND pid <> pg_backend_pid();

TABLESPACE — 디스크 분리

CREATE TABLESPACE fast_ssd LOCATION '/mnt/nvme/pgdata';

CREATE DATABASE hot_data TABLESPACE fast_ssd;
-- 또는 특정 테이블만
ALTER TABLE huge_table SET TABLESPACE fast_ssd;

활용: - 자주 쓰는 데이터 = SSD - 옛 로그·아카이브 = HDD (저렴) - 인덱스만 별도 SSD

대규모 운영 표준. 소규모 = pg_default 한 곳.

데이터베이스 크기·통계

-- 모든 DB 크기
SELECT datname, pg_size_pretty(pg_database_size(datname)) AS size
FROM pg_database
ORDER BY pg_database_size(datname) DESC;

-- 특정 DB 안 테이블 크기
SELECT
    schemaname || '.' || tablename AS table,
    pg_size_pretty(pg_total_relation_size(relid)) AS total,
    pg_size_pretty(pg_relation_size(relid)) AS data,
    pg_size_pretty(pg_indexes_size(relid)) AS indexes
FROM pg_stat_user_tables
ORDER BY pg_total_relation_size(relid) DESC LIMIT 10;

운영 정기 점검 항목.

활성 연결 모니터

SELECT
    datname,
    pid,
    usename,
    application_name,
    client_addr,
    state,
    query_start,
    LEFT(query, 60) AS query
FROM pg_stat_activity
WHERE datname IS NOT NULL
ORDER BY query_start;

state = active·idle·idle in transaction. idle in transaction 오래 = 트랜잭션 안 열어 둠 → bloat 위험.

오래된 트랜잭션 끊기

SELECT pg_terminate_backend(pid)
FROM pg_stat_activity
WHERE state = 'idle in transaction'
AND now() - state_change > INTERVAL '10 minutes';

운영 cron 으로 자동 정리.

데이터베이스 통계

SELECT
    datname,
    numbackends AS connections,
    xact_commit, xact_rollback,
    blks_hit, blks_read,
    ROUND(blks_hit * 100.0 / NULLIF(blks_hit + blks_read, 0), 2) AS cache_hit_pct,
    tup_returned, tup_fetched,
    tup_inserted, tup_updated, tup_deleted,
    conflicts, temp_files, temp_bytes,
    deadlocks
FROM pg_stat_database
WHERE datname IS NOT NULL;

전체 DB 통계. cache_hit_pct < 95% = 메모리 부족 신호.

RDS·Aurora 의 데이터베이스 관리

RDS = 일반 PG 와 거의 같음. 단: - 슈퍼유저 → rds_superuser (제한) - 일부 확장만 활성화 가능 - 파라미터는 Parameter Group 으로

Aurora = 추가 도구: - 자동 Read Replica - Backtrack (시간 되돌리기) - Database cloning (빠른 복제 — Copy-on-Write)

운영 자동화 — IaC

# Terraform
resource "aws_db_instance" "main" {
  identifier     = "prod-pg"
  engine         = "postgres"
  engine_version = "18"
  instance_class = "db.t4g.medium"
  allocated_storage = 100
  storage_type      = "gp3"

  db_name  = "appdb"
  username = "app_admin"
  password = data.aws_secretsmanager_secret_version.db.secret_string

  multi_az               = true
  backup_retention_period = 7
  performance_insights_enabled = true

  parameter_group_name = aws_db_parameter_group.main.name
}

운영 = IaC 무조건. 설정 코드화·재현 가능.

함정 5가지

(1) template1 오염

template1 에 박은 객체 = 모든 새 DB 에 복제. template0 사용.

(2) 인코딩·로케일 잘못

운영 가동 후 변경 = DB 재생성 필요. 처음부터 UTF8 + ko_KR.UTF-8.

(3) CONNECTION LIMIT 없음

특정 DB 가 모든 연결 차지 → 다른 DB 영향. 적정 한도.

(4) idle in transaction 누적

트랜잭션 안 열어 두고 잊음 = bloat. 자동 정리.

(5) TABLESPACE 잘못 사용

소규모에 TABLESPACE 분리 = 관리 부담. 큰 시스템부터.

🎯 DB 운영 5룰

(1) template0 + UTF8 + ko_KR.UTF-8. (2) CONNECTION LIMIT 적정. (3) pg_stat_activity·pg_stat_database 모니터. (4) idle in transaction 자동 정리. (5) IaC 로 설정 코드화.

한 줄 정리 — CREATE DATABASE 운영 옵션 + TEMPLATE 시스템 + TABLESPACE 분리. pg_stat_activity·pg_stat_database 모니터링. idle in transaction 정리. ALTER DATABASE SET 으로 DB 별 설정. RDS = Parameter Group + IaC.

시험 직전 한 번 더 — DB 관리 입문자가 매번 헷갈리는 것

  • CREATE DATABASE = TEMPLATE template0 + UTF8 + ko_KR
  • template0 vs template1 = template0 깨끗
  • IS_TEMPLATE = 다른 DB 가 복제 가능
  • ALLOW_CONNECTIONS = 차단·허용
  • TABLESPACE = 디스크 영역 분리
  • CONNECTION LIMIT 적정
  • ALTER DATABASE SET = DB 별 설정
  • timezone·search_path·work_mem 등
  • pg_dump -Fc = 운영 백업
  • pg_restore = 복원
  • ALTER DATABASE RENAME
  • SET TABLESPACE
  • pg_stat_activity = 활성 연결
  • state = active·idle·idle in transaction
  • idle in transaction 오래 = bloat 위험
  • pg_terminate_backend(pid)
  • pg_stat_database = DB 전체 통계
  • cache_hit_pct < 95% = 메모리 부족
  • pg_database_size = DB 크기
  • pg_total_relation_size = 테이블 + 인덱스
  • pg_indexes_size = 인덱스만
  • RDS = rds_superuser
  • Aurora = Backtrack·Database cloning
  • IaC = Terraform·Pulumi
  • multi_az = 운영 무조건
  • backup_retention_period = 7~30일
  • performance_insights = RDS 표준
  • 한국 운영 = template0 + UTF8 + IaC

시리즈 다른 편

시리즈 다음 글

다음 글(46편)에서는 백업·복구 — pg_dump·pg_basebackup·PITR.

공식 문서: PostgreSQL 18 — Managing Databases에서 더 자세한 사양을 확인할 수 있어요.

※ 이 포스팅은 쿠팡 파트너스 활동의 일환으로, 이에 따른 일정액의 수수료를 제공받습니다.

답글 남기기

error: Content is protected !!