테스트 DB 분리와 TransactionTestCase의 사용 시점
Django 테스트의 독립성을 보장하기 위한 테스트 DB 분리 메커니즘과 특정 상황에서 필요한 TransactionTestCase의 정확한 사용법
테스트 DB 분리의 필요성
독립성(Isolation) 보장이 핵심
데이터 오염 방지: 테스트 실행 중 생성/수정/삭제된 데이터가 실제 DB를 오염시키는 상황 방지
의존성 제거: 다른 테스트 결과나 기존 데이터에 의존하지 않는 안정적인 테스트 환경 구성
심각한 사고 예방: 실수로 운영 DB에 위험한 쿼리를 실행하는 상황 차단
Django는 테스트 실행 시 기존 DB와 완전히 독립된 별도의 테스트 DB를 자동 생성하여 사용
Django 테스트 DB 생성 메커니즘
manage.py test실행설정(settings.py)에 명시된 DB 정보 앞에 'test_' 붙여 새 DB 생성
Migration 실행하여 최신 스키마 적용
개별 테스트 실행
모든 테스트 종료 후 'test_' DB 삭제
성능 최적화: SQLite In-memory 모드 사용으로 테스트 속도 향상 가능
TestCase vs TransactionTestCase 핵심 차이
격리 방식
DB 트랜잭션으로 감싼 후 롤백
테이블을 비움(Truncate)
속도
빠름
느림
DB Commit
실제 COMMIT 발생하지 않음
실제 COMMIT 발생
주 사용처
대부분의 단위/통합 테스트
트랜잭션 동작 테스트
기본 원칙: 항상 TestCase를 기본으로 사용하고, TransactionTestCase는 꼭 필요한 특정 상황에서만 제한적으로 사용
TransactionTestCase 사용 시점
1. transaction.on_commit() 동작 테스트
현재 DB 트랜잭션이 성공적으로 커밋되었을 때만 특정 함수를 실행하는 로직 테스트
TestCase: COMMIT이 발생하지 않아 on_commit 콜백이 실행되지 않음
TransactionTestCase: 실제 COMMIT 실행으로 on_commit 콜백 정상 실행
2. 여러 스레드/프로세스 간 동작 테스트
별도의 스레드나 프로세스가 DB 데이터를 공유해야 하는 경우
웹소켓 로직이나 병렬 처리 로직 테스트에 필요
3. 데이터베이스 고유의 제약 조건 테스트
COMMIT 시점에만 검사되는 특정 제약 조건(DEFERRABLE 제약 등) 테스트
실무 주의사항
성능 저하 인지: TransactionTestCase는 TestCase보다 훨씬 느려 전체 테스트 스위트 실행 시간을 크게 증가시킴
최소한 사용: 꼭 필요한 곳에만 제한적으로 사용
reset_sequences: 기본적으로 각 테스트 후 PK 시퀀스도 리셋되어 매번 id=1부터 시작
Last updated
