Database
글 14편 · 학습 노트 1편 포함
-
Expand/Migrate/Contract란?
컬럼 이관은 Expand/Migrate/Contract를 따랐지만, 인스턴스 1대와 AllAtOnce 배포가 무중단을 막았다
한 줄로 Expand/Migrate/Contract는 스키마 변경을 세 단계로 쪼개는 방식이다. 새 구조를 추가하고(Expand), 데이터를 옮긴 뒤(Migrate), 옛 구조는 한참 뒤에 지운다(Contract). 회사 프로젝트의 운영 DB 이관을 조사해 보니 DDL은 이미 이 ...
-
Redis Pub/Sub 은 메시지를 보관하지 않는다
Pub/Sub · List · Streams 중 무엇을 고르나
Redis 로 메시지를 나르는 방법은 세 가지다. Pub/Sub, List, Streams. 셋 다 “A 가 보내고 B 가 받는다”를 해내지만, 고르는 기준은 성능도 문법도 아니다. 공식 문서에는 자료구조 선택 가이드 가 따로 있는데, 거기서 Pub/Sub 은 다뤄지지 않는다. P...
-
감사로그 IP 컬럼은 왜 varchar(45)여야 하는가 — STRICT 모드가 드러낸 것
STRICT 모드가 드러낸 감사로그 IP 잘림을 컬럼 확장과 길이 제한으로 처리했다
한 줄로 감사로그의 ip_address 컬럼이 varchar(16)인데 IPv6 주소는 최대 39자다. 지금까지는 DB가 조용히 잘라 저장하고 성공으로 처리했고, STRICT_TRANS_TABLES를 켜자 그 자리가 ERROR 1406으로 드러났다. 컬럼을 45로 넓히고, 애플리케...
-
캐시가 아니라 자로 쓴 Redis
통계 API 응답시간을 직접 재기
관리자 화면에 “통계 API 평균 응답시간” 을 띄워야 했다. 통계 API 는 집계 쿼리가 무거워 느려지면 먼저 티가 나는 쪽이라, 지금 얼마나 걸리는지를 화면에서 보고 싶었다. APM 을 붙이는 선택지가 있었지만 그러지 않았다. 알고 싶은 것은 특정 URL 접두사 하나의 평균 이...
-
장부만 지우고 세션은 살려뒀다
동시 접속 기기 제한이 안 걸린 이유
구독 플랜별로 동시 접속 기기 수를 제한하는 기능이다. 무료는 1대, 상위 플랜은 그 이상. Redis 에 사용자별 세션 목록을 두고, 로그인할 때 개수를 세어 넘으면 막는다. 만들고 나서 테스트했더니 제한이 걸리는데도 다른 기기가 계속 쓰였다. 로그인 화면에서는 “기존 기기를 종...
-
GROUP BY 축이 한 줄 달라서 배출량이 2배가 됐다
문제: 같은 투입량이 공정마다 전액 계상됐다 두 CTE의 GROUP BY 축이 달랐다. -- 산출 쪽: 공정별 GROUP BY lup.id, match_key -- 투입 쪽: LCA 전역 (match_key 당 1행) GROUP BY lup.lca_id, match_key 이 둘을...
-
ddl-auto: update 의 빈틈을 메웠다
보완 DDL 자동화로 채운 것
Flyway를 걷어낸 뒤 남은 숙제 이전 글: Flyway를 도입하고 3주 만에 걷어낸 이야기 걷어낸 뒤 스키마 관리 방식 JPA ddl-auto 사람이 손으로 적용하는 SQL 파일 묶음(db/manual/*.sql) 구멍 두 가지 stg 환경은 ddl-auto: validate ...
-
캐시를 고쳤는데 안 빨라졌다
문제: “데이터 조회가 느리다” 사용자 리포트는 이 한 줄이었다. 화면 — 배출량 산정의 원데이터 목록 탭 증상 — 목록이 뜨기까지 눈에 띄게 대기 주어진 정보 — 그게 전부. 어느 쿼리인지, 어느 카테고리인지 없음 여기서 두 갈래가 갈린다. 의심 가는 곳을 고칠 것인가, 어디가 ...
-
읽을 때마다 CTE 5개를 풀스캔했다
뷰를 물질화 테이블로 바꾸기
읽을 때마다 5개 CTE를 풀스캔하고 있었다 대상 — 대시보드 조회에 쓰이는 엔티티 하나 매핑 — @Subselect로 매핑된 뷰 구성 — CTE 5개를 엮은 집계 뷰 MySQL의 동작 — 이 뷰를 실체화해두지 않음. 조회할 때마다 전체 재계산 즉 화면을 열 때마다 풀스캔 판단 기...
-
Flyway 를 22일 만에 걷어냈다
도입보다 철수에서 배운 것
도입과 철수 사이 22일 도입 — 2026년 5월 13일 철수 — 6월 4일 기간 — 22일 그 사이 FlywayConfig — 221줄까지 성장 후 통째로 삭제 성공담이 아니라 철수 회고다. 왜 도입했나 프로젝트 구조: 빌드 — Gradle 멀티모듈 7개 (common / sha...
-
두 단계 조인을 버리고 역정규화했다
백필 마이그레이션까지
문제 장비 A의 소속 조직 파악 — 두 단계 조인 필요 A ──(customer_sq)──> B ──(매핑 테이블)──> 조직 A는 조직을 직접 갖지 않음 A → 고객 B에 부착 B → 조직 매핑 테이블을 통해 조직에 연결 정규화 관점에서는 정상 — 조직 정보가 한 곳에...
-
GIN trigram 인덱스를 만들었는데 왜 안 빨라지지?
인덱스를 만든 날과 인덱스가 실제로 쓰인 날이 13일 떨어져 있다 2026-03-12 — GIN trigram 인덱스 추가 2026-03-25 — 인덱스가 쿼리 플랜에 처음 등장 그 사이 13일 동안 인덱스는 디스크만 차지 이 글의 주제 — 그 13일 문제 환경: Spring Bo...
-
바인드 파라미터 65,535개 한도에 부딪혔다
PostgreSQL 이 한 번에 받는 값의 상한
문제 기능: 엑셀로 장비 매핑 정보 일괄 업로드 수백 행 → 정상 동작 실제 현장 데이터 수만 행 → 배치 INSERT에서 터짐 구현: MyBatis <foreach> 멀티 로우 INSERT 행이 늘수록 SQL 하나의 바인드 파라미터 개수도 선형 증가 그 개수에 상한 존...
학습 노트
책·강의를 따라 적은 정리 1편. 2026 이전에 쓴 것이다.