TIL 20260710

juni·2026년 7월 10일

TIL

목록 보기
399/468

0710 백엔드 실무 심화 (17/N): 데이터 마이그레이션, 백필과 운영 데이터 변경 전략


✅ 1. 데이터 마이그레이션이란 무엇인가?

  • 데이터 마이그레이션(Data Migration)은 DB 구조나 데이터를 새로운 형태로 변경하는 작업입니다.
  • 백엔드 실무에서는 테이블 추가, 컬럼 추가, enum 변경, 기존 데이터 보정, 상태값 변경, 누락 데이터 채우기 같은 작업이 자주 발생합니다.
  • 단순히 Prisma schema를 바꾸고 migration을 실행하는 것뿐 아니라, 운영 중인 데이터가 안전하게 변환되는지까지 봐야 합니다.
기존 DB 구조
  ↓
새 기능 요구사항 반영
  ↓
schema 변경
  ↓
migration 실행
  ↓
기존 데이터 보정
  ↓
새 코드 배포

➕ 1-1. 마이그레이션이 중요한 이유

  • 운영 DB에는 실제 고객, 주문, 상담, 관리자 데이터가 들어 있습니다.
  • 잘못된 migration은 서비스 장애뿐 아니라 데이터 손실로 이어질 수 있습니다.
  • 코드 롤백은 비교적 쉽지만, DB 변경 롤백은 훨씬 어렵습니다.
  • 그래서 운영 DB 변경은 항상 조심해야 합니다.
코드 오류:
이전 커밋으로 롤백 가능

DB 데이터 삭제:
복구가 어렵거나 스냅샷 복원이 필요

✅ 2. Schema Migration과 Data Migration

  • 마이그레이션은 크게 Schema Migration과 Data Migration으로 나눌 수 있습니다.
구분의미예시
Schema MigrationDB 구조 변경테이블 추가, 컬럼 추가, 인덱스 추가
Data Migration기존 데이터 변경상태값 변환, 누락 값 채우기
Backfill새 컬럼에 기존 데이터 채우기completedAt 채우기
Seed초기 데이터 입력관리자 권한, 기본 설정값

➕ 2-1. Schema Migration 예시

Consult 테이블에 completedAt 컬럼 추가
ExportJob 테이블 추가
AdminActionLog 테이블 추가
phone 컬럼에 index 추가

➕ 2-2. Data Migration 예시

status='COMPLETE' 값을 status='DONE'으로 변경
기존 완료 상담의 completedAt을 updatedAt 기준으로 채우기
기존 상품 URL slug를 생성해서 저장
기존 관리자 role 값을 새 enum 구조로 변환
  • 구조 변경과 데이터 변경은 같이 보이지만 위험도가 다릅니다.
  • 특히 기존 데이터를 대량으로 수정하는 작업은 성능과 복구 전략까지 고려해야 합니다.

✅ 3. Prisma Migration 기본 흐름

  • Prisma에서는 schema.prisma를 수정한 뒤 migration 파일을 생성하고 DB에 반영합니다.

➕ 3-1. 개발 환경에서 migration 생성

npx prisma migrate dev --name add-consult-completed-at
  • 개발 환경에서는 migrate dev로 migration 파일을 만들고 로컬 DB에 적용할 수 있습니다.
  • migration 파일은 Git에 커밋해야 합니다.

➕ 3-2. 운영 환경에서 migration 적용

npx prisma migrate deploy
  • 운영에서는 migrate deploy를 사용합니다.
  • 운영에서 migrate dev, db push --force-reset, migrate reset을 쓰면 안 됩니다.
운영에서 금지:
npx prisma migrate reset
npx prisma db push --force-reset
npx prisma migrate dev

운영에서 사용:
npx prisma migrate deploy

✅ 4. 운영 DB 변경 전 반드시 확인할 것

➕ 4-1. 변경 영향 범위

  • 어떤 테이블이 바뀌는가?
  • 어떤 API가 영향을 받는가?
  • 어떤 관리자 화면이 영향을 받는가?
  • Queue Worker, Batch, Webhook도 영향을 받는가?
  • 기존 데이터와 새 코드가 호환되는가?
예시:
Consult.status enum 변경
  ↓
상담 목록 필터 영향
상태 변경 API 영향
엑셀 다운로드 영향
통계 배치 영향
관리자 상태 배지 영향

➕ 4-2. 데이터 양

  • 테이블 row가 몇 개인지 확인해야 합니다.
  • 데이터가 많을수록 migration 시간이 길어지고 lock이 걸릴 수 있습니다.
SELECT COUNT(*) FROM "Consult";
  • 작은 테이블에서는 문제가 없던 변경도, 수십만~수백만 건 테이블에서는 장애가 될 수 있습니다.

➕ 4-3. 복구 방법

  • 문제가 생기면 어떻게 복구할지 미리 정해야 합니다.
  • 위험한 작업 전에는 RDS 스냅샷이나 DB dump를 고려해야 합니다.
위험한 변경:
컬럼 삭제
테이블 삭제
대량 update
unique 제약 추가
enum 변경
  • 이런 작업은 배포 전 백업이 사실상 필수입니다.

✅ 5. 안전한 컬럼 추가 전략

  • 운영 DB에 새 컬럼을 추가할 때 가장 안전한 방식은 nullable 컬럼 추가 → 코드 적용 → 데이터 백필 → NOT NULL 전환 순서입니다.

➕ 5-1. 위험한 방식

model Consult {
  id          Int      @id @default(autoincrement())
  completedAt DateTime
}
  • 기존 row가 이미 많은데 기본값 없는 NOT NULL 컬럼을 추가하면 실패하거나 테이블 lock이 길어질 수 있습니다.
  • 기존 데이터에 어떤 값을 넣을지 명확하지 않습니다.

➕ 5-2. 안전한 방식

model Consult {
  id          Int       @id @default(autoincrement())
  completedAt DateTime?
}
1. nullable 컬럼 추가
2. 새 코드에서 completedAt 저장
3. 기존 데이터 backfill
4. 모든 데이터 채워졌는지 검증
5. 필요하면 NOT NULL로 변경
  • 기능 배포와 데이터 보정을 단계별로 나누면 롤백이 쉬워집니다.
  • 운영에서는 한 번에 완벽하게 바꾸려고 하면 위험합니다.

✅ 6. Backfill이란 무엇인가?

  • Backfill은 새로 추가한 컬럼이나 테이블에 기존 데이터를 기준으로 값을 채워 넣는 작업입니다.
  • 예를 들어 completedAt 컬럼을 새로 추가했는데, 기존 완료 상담 데이터에도 완료 시간을 채워야 한다면 backfill이 필요합니다.

➕ 6-1. 예시

새 요구사항:
상담 완료 시간을 통계에 사용하고 싶음

기존 데이터:
status = DONE
completedAt = null

Backfill:
status가 DONE인 데이터의 completedAt을 updatedAt 기준으로 채움

➕ 6-2. SQL 예시

UPDATE "Consult"
SET "completedAt" = "updatedAt"
WHERE "status" = 'DONE'
  AND "completedAt" IS NULL;
  • 간단한 작업은 SQL로 처리할 수 있습니다.
  • 하지만 데이터가 많으면 한 번에 update하지 말고 batch 단위로 나누는 것이 좋습니다.

✅ 7. 대량 Backfill 주의점

  • 대량 update는 DB 부하를 만들 수 있습니다.
  • 운영 시간에 큰 update를 실행하면 서비스 응답이 느려질 수 있습니다.

➕ 7-1. 위험한 방식

UPDATE "Consult"
SET "source" = 'UNKNOWN'
WHERE "source" IS NULL;
  • 대상 row가 수십만 건이면 긴 lock과 부하가 발생할 수 있습니다.

➕ 7-2. Batch 단위 처리

1. 1,000건 조회
2. update
3. 잠시 대기
4. 다음 1,000건 처리
5. 반복

➕ 7-3. Prisma 예시

async backfillConsultCompletedAt() {
  const batchSize = 1000;

  while (true) {
    const rows = await this.prisma.consult.findMany({
      where: {
        status: 'DONE',
        completedAt: null,
      },
      select: {
        id: true,
        updatedAt: true,
      },
      take: batchSize,
      orderBy: {
        id: 'asc',
      },
    });

    if (rows.length === 0) {
      break;
    }

    for (const row of rows) {
      await this.prisma.consult.update({
        where: {
          id: row.id,
        },
        data: {
          completedAt: row.updatedAt,
        },
      });
    }

    await new Promise((resolve) => setTimeout(resolve, 200));
  }
}
  • 간단히 이해하기 위한 예시입니다.
  • 실제로는 updateMany를 적절히 섞거나, cursor 기준으로 처리하고, 실행 이력을 남기는 것이 좋습니다.

✅ 8. Backfill 작업 이력 관리

  • Backfill도 운영 작업입니다.
  • 언제, 누가, 어떤 기준으로, 몇 건을 수정했는지 남겨야 합니다.

➕ 8-1. DataMigrationLog 모델 예시

model DataMigrationLog {
  id             Int      @id @default(autoincrement())
  name           String
  status         String
  targetTable    String?
  processedCount Int      @default(0)
  successCount   Int      @default(0)
  failCount      Int      @default(0)
  startedAt      DateTime @default(now())
  endedAt        DateTime?
  errorMessage   String?
  createdBy      String?
  createdAt      DateTime @default(now())

  @@index([name, status])
  @@index([startedAt])
}

➕ 8-2. 남기면 좋은 정보

  • 작업 이름
  • 대상 테이블
  • 처리 조건
  • 처리 건수
  • 성공/실패 건수
  • 시작/종료 시간
  • 실행자
  • 에러 메시지
name=BACKFILL_CONSULT_COMPLETED_AT
targetTable=Consult
status=SUCCESS
processedCount=15230
duration=3m 20s
  • 나중에 데이터가 이상할 때 “언제 어떤 보정이 들어갔는지” 추적할 수 있습니다.

✅ 9. 인덱스 추가 전략

  • 인덱스는 검색 성능을 높여주지만, 운영 DB에 추가할 때는 주의가 필요합니다.
  • 큰 테이블에 인덱스를 추가하면 시간이 오래 걸리고 write 성능에 영향을 줄 수 있습니다.

➕ 9-1. 인덱스 추가 예시

model Consult {
  id        Int      @id @default(autoincrement())
  phone     String
  status    String
  source    String?
  createdAt DateTime @default(now())

  @@index([status, createdAt])
  @@index([source, createdAt])
  @@index([phone])
}

➕ 9-2. 인덱스 추가 전 확인

이 조건으로 실제 검색이 자주 발생하는가?
데이터가 얼마나 많은가?
쓰기 작업이 많은 테이블인가?
기존 인덱스와 중복되지 않는가?
복합 인덱스 순서가 맞는가?
  • 인덱스는 많을수록 좋은 것이 아닙니다.
  • 읽기는 빨라질 수 있지만, insert/update/delete는 느려질 수 있습니다.

✅ 10. Unique 제약 추가 전 데이터 정리

  • 기존 테이블에 unique 제약을 추가하려면 먼저 중복 데이터가 없는지 확인해야 합니다.
  • 중복 데이터가 있으면 migration이 실패합니다.

➕ 10-1. 중복 확인 SQL 예시

SELECT phone, "productId", COUNT(*)
FROM "Consult"
GROUP BY phone, "productId"
HAVING COUNT(*) > 1;

➕ 10-2. 처리 흐름

1. 중복 데이터 확인
2. 어떤 row를 유지할지 기준 결정
3. 중복 row 정리 또는 병합
4. unique 제약 추가
5. 새 코드에서 P2002 처리
  • 중복 데이터 정리는 업무 기준이 필요합니다.
  • 무작정 오래된 데이터를 삭제하면 운영 이력이 사라질 수 있습니다.

✅ 11. Enum 변경 전략

  • 상태값 enum 변경은 생각보다 위험합니다.
  • 기존 DB 값, 백엔드 코드, 프론트 표시명, 통계, 필터, 엑셀 다운로드가 모두 영향을 받을 수 있습니다.

➕ 11-1. 위험한 변경 예시

기존:
WAITING

변경:
PENDING

문제:
기존 DB에는 WAITING 값이 남아 있음
새 코드는 PENDING만 처리함
관리자 필터에서 누락됨

➕ 11-2. 안전한 변경 흐름

1. 새 enum 값을 추가
2. 코드에서 기존 값과 새 값을 모두 처리
3. 기존 데이터를 새 값으로 변환
4. 검증
5. 기존 enum 값 제거
  • enum 값 삭제는 마지막 단계로 미루는 것이 안전합니다.
  • 운영에서는 기존 데이터가 완전히 변환되었는지 먼저 확인해야 합니다.

✅ 12. Seed 데이터 관리

  • Seed는 서비스 실행에 필요한 초기 데이터를 넣는 작업입니다.
  • 예를 들어 관리자 권한, 기본 역할, 기본 설정값, 카테고리 코드, 상태 코드 등을 넣을 수 있습니다.

➕ 12-1. Seed 대상 예시

SUPER_ADMIN 역할
기본 Permission 목록
FeatureFlag 기본값
상품 카테고리 코드
알림톡 템플릿 코드
시스템 설정값
기본 배너 위치 코드

➕ 12-2. Prisma seed 예시

async function main() {
  await prisma.role.upsert({
    where: {
      name: 'SUPER_ADMIN',
    },
    update: {},
    create: {
      name: 'SUPER_ADMIN',
    },
  });

  await prisma.featureFlag.upsert({
    where: {
      key: 'PREORDER_OPEN',
    },
    update: {},
    create: {
      key: 'PREORDER_OPEN',
      isEnabled: false,
      description: '사전예약 오픈 여부',
    },
  });
}

main();
  • Seed는 여러 번 실행해도 중복 데이터가 생기지 않게 upsert로 작성하는 것이 좋습니다.
  • 운영 seed는 특히 조심해야 합니다.

✅ 13. 운영 Seed 주의점

  • 개발용 seed와 운영용 seed를 구분해야 합니다.
  • 운영 DB에 테스트 관리자, 테스트 상품, 가짜 상담 신청 데이터를 넣으면 안 됩니다.

➕ 13-1. 나쁜 예시

운영 seed에 포함:
test@test.com 관리자
가짜 고객 데이터
테스트 주문
샘플 상담 신청

➕ 13-2. 좋은 기준

운영 seed에 포함 가능:
기본 Role
기본 Permission
기본 FeatureFlag
시스템 설정 key
알림 템플릿 코드
  • 운영 seed는 서비스 운영에 필요한 최소 데이터만 넣는 것이 좋습니다.
  • 테스트 데이터는 개발/스테이징 환경에만 있어야 합니다.

✅ 14. 데이터 정정 작업

  • 운영 중에는 잘못 들어간 데이터를 수정해야 할 때가 있습니다.
  • 예를 들어 특정 상담 신청의 유입경로가 잘못 저장되었거나, 상품 가격이 잘못 들어간 경우입니다.

➕ 14-1. 데이터 정정 전 확인

어떤 데이터가 잘못되었는가?
몇 건이 영향을 받았는가?
수정 기준은 명확한가?
수정 전 값을 백업할 수 있는가?
수정 후 검증 쿼리는 있는가?
운영자/대표에게 확인이 필요한가?

➕ 14-2. 정정 SQL 예시

UPDATE "Consult"
SET "source" = 'NAVER'
WHERE "id" IN (101, 102, 103)
  AND "source" = 'UNKNOWN';
  • WHERE 조건을 최대한 구체적으로 작성해야 합니다.
  • update/delete SQL을 실행하기 전에 같은 조건으로 select를 먼저 실행하는 습관이 필요합니다.
SELECT id, source
FROM "Consult"
WHERE "id" IN (101, 102, 103)
  AND "source" = 'UNKNOWN';

✅ 15. Delete보다 Soft Delete

  • 운영 데이터는 실제 삭제보다 soft delete가 안전한 경우가 많습니다.

➕ 15-1. 실제 삭제의 위험

DELETE FROM "Consult"
WHERE "createdAt" < '2026-01-01';
  • 잘못 실행하면 복구가 어렵습니다.
  • 상담, 주문, 관리자 이력처럼 추적이 필요한 데이터는 삭제하면 안 되는 경우가 많습니다.

➕ 15-2. Soft Delete 예시

model Consult {
  id        Int       @id @default(autoincrement())
  status    String
  deletedAt DateTime?
  createdAt DateTime  @default(now())
}
UPDATE "Consult"
SET "deletedAt" = NOW()
WHERE "id" = 123;
  • 목록에서는 deletedAt IS NULL 조건으로 제외합니다.
  • 필요하면 복구할 수 있습니다.

✅ 16. 운영 Migration 배포 순서

  • DB migration이 있는 배포는 순서가 중요합니다.
  • 특히 프론트, 백엔드, DB가 함께 바뀌는 경우 중간 상태에서도 서비스가 동작해야 합니다.

➕ 16-1. 안전한 순서 예시

1. 새 nullable 컬럼 추가 migration
2. 백엔드가 새 컬럼을 쓰되 기존 데이터도 처리하도록 배포
3. 기존 데이터 backfill
4. 프론트에서 새 필드 표시
5. 충분히 검증
6. 필요하면 NOT NULL 또는 기존 컬럼 제거

➕ 16-2. 위험한 순서

1. 기존 컬럼 삭제
2. 백엔드 배포
3. 프론트 배포

문제:
구버전 백엔드/프론트가 삭제된 컬럼을 참조하면 즉시 장애
  • 운영에서는 “한 번에 바꾸기”보다 “나눠서 바꾸기”가 안전합니다.

✅ 17. Migration과 Rollback

  • DB migration은 코드처럼 쉽게 되돌릴 수 없습니다.
  • rollback migration을 만들 수는 있지만, 데이터 삭제가 포함되면 복구가 어려울 수 있습니다.

➕ 17-1. 롤백 가능한 변경

nullable 컬럼 추가
새 테이블 추가
새 인덱스 추가
새 enum 값 추가

➕ 17-2. 롤백 어려운 변경

컬럼 삭제
테이블 삭제
데이터 대량 update
enum 값 삭제
데이터 포맷 변환
unique 제약 추가 후 데이터 정리
  • 위험한 변경은 배포 전 RDS 스냅샷이 필요할 수 있습니다.
  • 롤백 계획 없이 운영 DB를 바꾸는 건 피해야 합니다.

✅ 18. Migration 검증 쿼리

  • migration이나 backfill 후에는 반드시 검증 쿼리를 실행해야 합니다.

➕ 18-1. completedAt backfill 검증

SELECT COUNT(*)
FROM "Consult"
WHERE "status" = 'DONE'
  AND "completedAt" IS NULL;
  • 결과가 0이어야 합니다.

➕ 18-2. 중복 데이터 검증

SELECT phone, "productId", COUNT(*)
FROM "Consult"
GROUP BY phone, "productId"
HAVING COUNT(*) > 1;
  • unique 제약 추가 전에는 중복이 없어야 합니다.

➕ 18-3. 상태값 검증

SELECT status, COUNT(*)
FROM "Consult"
GROUP BY status;
  • 예상하지 못한 상태값이 남아 있는지 확인할 수 있습니다.

✅ 19. Migration 문서화

  • 운영 DB를 변경한 작업은 문서로 남겨야 합니다.
  • 나중에 장애가 발생했을 때 어떤 migration이 원인이었는지 빠르게 찾을 수 있습니다.

➕ 19-1. 문서 템플릿

## Migration: 2026-07-10 add consult completedAt

### 목적
- 상담 완료 시간 기반 통계 계산을 위해 completedAt 컬럼 추가

### 변경 내용
- Consult.completedAt nullable 컬럼 추가
- status=DONE인 기존 데이터에 updatedAt 기준 backfill

### 영향 범위
- 상담 목록
- 상담 상태 변경 API
- 일별 통계 배치
- 엑셀 다운로드

### 배포 순서
1. schema migration 적용
2. 백엔드 배포
3. backfill 실행
4. 검증 쿼리 실행

### 검증 쿼리
```sql
SELECT COUNT(*)
FROM "Consult"
WHERE "status" = 'DONE'
  AND "completedAt" IS NULL;

롤백 계획

  • 코드 롤백 가능
  • completedAt 컬럼은 즉시 삭제하지 않고 유지
  • 문제 발생 시 해당 필드 사용 로직 비활성화

*   문서에는 목적, 변경 내용, 영향 범위, 검증 쿼리, 롤백 계획이 들어가야 합니다.
*   1인 개발자라도 이 기록은 반드시 도움이 됩니다.

---

### ✅ 20. 실무 체크리스트

#### ➕ 20-1. Migration 전 체크리스트

1.  변경 목적이 명확한가?
2.  영향받는 API와 화면을 확인했는가?
3.  Queue, Batch, Webhook 영향도 확인했는가?
4.  기존 데이터 수를 확인했는가?
5.  위험한 변경인지 분류했는가?
6.  RDS 스냅샷 또는 백업이 필요한가?
7.  운영에서 사용할 Prisma 명령어가 `migrate deploy`인지 확인했는가?
8.  rollback 또는 우회 전략이 있는가?

#### ➕ 20-2. Migration 실행 체크리스트

1.  운영 DB 연결 대상이 맞는가?
2.  migration 파일을 리뷰했는가?
3.  배포 시간과 배치 시간이 겹치지 않는가?
4.  migration 실행 로그를 확인했는가?
5.  대량 backfill은 batch 단위로 실행하는가?
6.  실행 중 DB 부하를 확인할 수 있는가?
7.  실패 시 즉시 중단하고 원인을 확인하는가?

#### ➕ 20-3. Migration 후 체크리스트

1.  검증 쿼리를 실행했는가?
2.  API health check가 정상인가?
3.  주요 관리자 기능이 정상인가?
4.  배치/Worker 에러가 없는가?
5.  알 수 없는 status나 null 값이 남아 있지 않은가?
6.  로그에 migration 관련 에러가 없는가?
7.  릴리즈 기록에 DB 변경을 남겼는가?
8.  필요 없는 임시 코드 제거 일정을 정했는가?

---

### ✅ 21. AI를 활용해 Migration/Backfill 계획을 만들 때 질문법

*   AI에게 migration을 물어볼 때는 단순히 “컬럼 추가해줘”가 아니라, 기존 데이터, 운영 배포 순서, 백필 기준, 롤백 가능성까지 함께 설명해야 합니다.

#### ➕ 21-1. 좋은 질문 예시

```txt id="ai-migration-question"
NestJS + Prisma + PostgreSQL 운영 서비스에서 Consult 테이블에 completedAt 컬럼을 추가하고 싶어.

상황:
1. Consult 테이블에는 기존 상담 신청 데이터가 약 15만 건 있음
2. 현재 status는 PENDING, CALLING, DONE, CANCELLED가 있음
3. 앞으로 DONE 상태가 되는 시점에 completedAt을 저장하고 싶음
4. 기존 DONE 데이터는 updatedAt 값을 기준으로 completedAt을 backfill하고 싶음
5. 일별 통계 배치와 엑셀 다운로드에서 completedAt을 사용할 예정
6. 운영 DB는 AWS RDS PostgreSQL
7. Prisma migration을 사용 중
8. 배포 중 상담 신청과 관리자 상태 변경이 계속 발생할 수 있음
9. 안전하게 여러 단계로 배포하고 싶음

요청:
- Prisma schema 변경안
- 안전한 migration 순서
- backfill 스크립트 설계
- batch 단위 처리 방법
- 검증 SQL
- 배포 전/후 체크리스트
- 롤백 또는 우회 전략
을 실무 기준으로 정리해줘.

➕ 21-2. AI 답변 검증 기준

  1. 운영에서 migrate reset이나 db push --force-reset을 권하지 않는가?
  2. 새 컬럼을 처음부터 무조건 NOT NULL로 추가하지 않는가?
  3. nullable 추가 → 코드 배포 → backfill → 검증 순서를 제안하는가?
  4. 대량 데이터 update를 batch 단위로 처리하라고 하는가?
  5. 기존 데이터 수와 DB 부하를 확인하라고 하는가?
  6. 검증 쿼리를 포함하는가?
  7. 롤백 어려운 변경을 구분하는가?
  8. migration 문서화와 릴리즈 기록을 권장하는가?

📌 요약

  • 데이터 마이그레이션은 DB 구조나 데이터를 새로운 형태로 변경하는 작업이며, 운영 서비스에서는 매우 조심해야 합니다.
  • Schema Migration은 테이블/컬럼/인덱스 같은 구조 변경이고, Data Migration은 기존 데이터를 새 기준에 맞게 보정하는 작업입니다.
  • Prisma 운영 환경에서는 migrate deploy를 사용해야 하며, migrate reset, db push --force-reset, migrate dev는 운영에서 사용하면 안 됩니다.
  • 새 컬럼은 처음부터 NOT NULL로 강제하기보다 nullable로 추가한 뒤, 코드 배포와 backfill을 거쳐 검증 후 제약을 강화하는 것이 안전합니다.
  • 대량 backfill은 한 번에 update하지 말고 batch 단위로 나누어 DB 부하와 lock 위험을 줄이는 것이 좋습니다.
  • Unique 제약을 추가하기 전에는 반드시 기존 중복 데이터를 확인하고 정리해야 합니다.
  • Enum 변경은 기존 값과 새 값을 함께 처리하는 기간을 두고, 데이터 변환이 끝난 뒤 기존 값을 제거하는 방식이 안전합니다.
  • 운영 seed는 기본 Role, Permission, FeatureFlag, 설정값처럼 서비스 운영에 필요한 최소 데이터만 넣고, 테스트 데이터는 운영에 넣으면 안 됩니다.
  • migration 후에는 검증 쿼리, health check, 주요 기능 확인, Worker/Batch 로그 확인까지 진행해야 합니다.
  • 운영 DB 변경은 목적, 영향 범위, 실행 순서, 검증 쿼리, 롤백 계획을 문서로 남겨야 나중에 장애 대응과 경력 정리에 모두 도움이 됩니다.

0개의 댓글