RBU — VACUUM 명령의 대안
RBU — VACUUM 명령의 대안
이 문서는 RBU(Resumable Bulk Update) 확장 기능을 설명해요. RBU는 데이터베이스를 온라인 상태로 유지하면서 점진적으로(incrementally) 갱신하거나 재구성할 수 있게 해 주는, VACUUM 명령의 대안이에요.
출처: 문서
본문
VACUUM 명령은 데이터베이스를 압축하고 정리하는 데 유용하지만, 수행하는 동안 데이터베이스에 배타적 잠금(exclusive lock)을 걸어 다른 작업이 불가능해져요. RBU(Resumable Bulk Update)는 대량의 변경을 점진적으로 수행할 수 있어, 큰 데이터베이스를 다룰 때 유리해요.
RBU는 두 개의 데이터베이스를 사용해요.
- 대상(target) 데이터베이스: 실제로 갱신할 데이터베이스
- RBU 데이터베이스: 대상 데이터베이스에 적용할 변경 내용을 담은 보조 데이터베이스
RBU 데이터베이스에는 각 대상 테이블에 대해 data_<tablename>(변경할 행 데이터)과 rbu_<tablename>(나중에 삭제할 행의 키)이라는 테이블들이 있어요. RBU는 이들을 순서대로 읽어 대상 테이블을 갱신해요.
RBU의 용도
RBU는 다음 상황에서 유용해요.
- 데이터베이스가 크고,
VACUUM처럼 한 번에 전체를 다시 쓰기 어려울 때 - 갱신 도중에도 데이터베이스를 읽기나 쓰기로 계속 사용해야 할 때
- 대량의 변경을 일괄로 적용하면서 진행 상황을 점검하고 싶을 때
RBU 확장 사용하기 (CLI)
명령줄 인터페이스(CLI)의 .load 명령으로 RBU 확장을 로드할 수 있어요.
.load ./rbu
.open rbu.db
SELECT rbu_master.submit('VACUUM');
rbu_master.submit()에 'VACUUM'을 넘기면, 현재 데이터베이스의 내용을 RBU 데이터베이스로 옮긴 뒤 대상 데이터베이스를 비워 둔 상태로 만들어, 이후 대상 데이터베이스를 다시 채우는 데 사용할 수 있어요.
RBU C API
C 프로그램에서는 RBU 확장의 C API(sqlite3rbu_* 함수)를 사용해 점진적 갱신을 제어할 수 있어요. 주요 함수는 다음과 같아요.
sqlite3rbu_open()— 대상 데이터베이스에서 RBU 객체를 생성해요.sqlite3rbu_step()— RBU 작업을 한 단계씩 수행해요.sqlite3rbu_close()— RBU 객체를 닫아요.sqlite3rbu_bp관련 — 중단 지점(checkpoint)을 만들어 나중에 이어서(resume) 진행할 수 있어요.
RBU C API의 전체 목록은 RBU C API 문서를 참고하세요.
RBU와 VACUUM 비교
| 특징 | VACUUM | RBU |
|---|---|---|
| 갱신 중 잠금 | 배타적 잠금 (다른 작업 불가) | 점진적이라 부분 갱신 가능 |
| 큰 데이터베이스 | 모든 데이터를 다시 씀 | 변경분만을 순차 적용 |
| 진행 상황 재개 | 지원 안 함 | 중단 후 재개(resume) 가능 |
예제
대상 데이터베이스의 특정 테이블을 재구성하려면, RBU 데이터베이스에 data_<tablename> 테이블로 원하는 새 내용을 넣고 RBU를 실행하면 돼요. RBU는 기존 테이블의 내용을 data_ 테이블의 내용으로 덮어써요.
RBU는 동기화(동일 구조의 다른 데이터 그룹 교체)나, 테이블 구조 변경이 필요할 때 VACUUM 대신 사용하기 좋아요.