컬렉션 리샤딩
이 페이지의 내용
버전 5.0에 추가.
이상적인 샤드 키를 사용하면 MongoDB가 클러스터 전체에 문서를 고르게 분산하는 동시에 일반적인 쿼리 패턴을 용이하게 할 수 있습니다. 샤드 키가 최적화되지 않으면 고르지 않은 데이터 분산으로 인해 성능 또는 확장 문제를 일으킬 수 있습니다.
MongoDB 5.0부터 컬렉션의 샤드 키를 변경하여 클러스터 전체의 데이터 분산을 변경할 수 있습니다.
MongoDB 8.0부터는 동일한 샤드 키 에서 컬렉션 을 재샤딩하여 샤드 키 를 변경하지 않고도 새 샤드를 포함하거나 다른 구역에 데이터를 재배포할 수 있습니다.
참고
컬렉션 을 리샤딩하기 전에 샤드 키 문제 해결 에서 일반적인 성능 및 확장 문제에 대한 정보와 해결 방법에 대한 조언 을 읽어보세요.
이 작업에 대하여
한 번에 하나의 컬렉션만 리샤딩할 수 있습니다.
writeConcernMajorityJournalDefault
은 이어야true
합니다.고유성 제약 조건이 있는 컬렉션을 리샤드하려면 새 샤드 키가 기존의 모든 고유 인덱스에 대한 고유 인덱스 요구 사항을 충족해야 합니다.
리샤딩 작업이 진행 중인 동안 리샤딩되는 컬렉션에서는 다음 명령 및 해당 셸 메서드가 지원되지 않습니다.
다음 명령과 메서드는 리샤딩 작업이 진행되는 동안 클러스터에서 지원되지 않습니다.
경고
리샤딩 작업 중에 위의 명령 중 하나를 사용하면 리샤딩 작업이 실패합니다.
리샤딩할 컬렉션 이 Atlas Search 를 사용하는 경우 리샤딩 작업이 완료되면 검색 인덱스 를 사용할 수 없게 됩니다. 리샤딩 작업이 완료되면 검색 인덱스 를 수동으로 다시 작성해야 합니다.
샤딩된 시계열 컬렉션은 다시 샤딩할 수 없습니다.
시작하기 전에
컬렉션을 리샤딩하기 전에 다음 요구 사항을 충족하는지 확인하세요.
애플리케이션 은 영향을 받는 컬렉션 이 쓰기를 차단하는 2초의 기간을 허용할 수 있습니다. 쓰기가 차단되는 기간 동안 애플리케이션 의 지연 시간 이 증가합니다.
워크로드가 이러한 요구 사항을 수용할 수 없는 경우에는 대신 샤드 키를 개선하는 것이 좋습니다.
데이터베이스는 다음과 같은 리소스 요구 사항을 충족합니다.
컬렉션 을 분산된 할 각 샤드 의 사용 가능한 저장 공간이 리샤딩하려는 컬렉션 크기와 총 인덱스 크기를 샤드 수로 나눈 값의 두 배 이상인지 확인합니다.
storage_req = ( ( collection_storage_size + index_size ) * 2 ) / shard_count 예를 들어 컬렉션에 2 TB의 데이터가 포함되어 있고 4개의 샤드에 400 GB 인덱스가 분산되어 있다고 가정해 보겠습니다. 이 컬렉션에서 리샤딩 작업을 수행하려면 각 샤드에 1.2 TB의 사용 가능한 스토리지.
1.2 TB storage = ( ( 2 TB collection + 0.4 TB index ) * 2 ) / 4 shards 스토리지 요구 사항을 충족하려면 리샤딩 작업 중에 다음 스토리지 계층으로 업그레이드해야 할 수 있습니다. 작업이 완료되면 축소할 수 있습니다.
I/O 용량 이 50% 미만인지 확인합니다.
CPU 로드가 80% 미만인지 확인합니다.
중요
이러한 요구 사항은 데이터베이스에 의해 적용되지 않습니다. 충분한 리소스를 할당하지 못하면 다음과 같은 결과가 발생할 수 있습니다.
데이터베이스 공간이 부족하여 종료되는 경우
성능 저하
작업이 예상보다 오래 걸리는 경우
애플리케이션 에 트래픽이 적은 기간이 있는 경우 가능하면 해당 기간 동안 컬렉션 에 대해 이 작업을 수행합니다.
현재 샤드 키 와 새 샤드 키 를 모두 사용하려면 애플리케이션의 쿼리를 다시 작성해야 합니다.
팁
애플리케이션 이 다운타임을 견딜 수 있는 경우 다음 단계를 수행하여 현재 샤드 키와 새 샤드 키를 모두 사용하도록 애플리케이션의 쿼리를 다시 작성하지 않도록 할 수 있습니다.
애플리케이션을 중지하세요.
새 샤드 키 를 사용하도록 애플리케이션 을 다시 작성합니다.
리샤딩이 완료될 때까지 기다립니다. 리샤딩 프로세스 를 모니터 하려면
$currentOp
파이프라인 단계를 사용합니다.재작성된 애플리케이션 을 배포합니다.
쿼리 필터하다 에 현재 샤드 키 고유 필드 (예:
_id
)가 포함되지 않은 경우 다음 쿼리는 리샤딩이 완료되기 전에 오류를 반환합니다.최적의 성능을 위해 새 샤드 키를 포함하도록 다른 쿼리도 다시 작성하는 것이 좋습니다.
리샤딩 작업이 완료되면 쿼리에서 이전 샤드 키를 제거할 수 있습니다.
현재 진행 중인 인덱스 빌드가 없습니다.
db.currentOp()
을(를) 사용하여 실행 중인 인덱스 빌드를 확인합니다.db.adminCommand( { currentOp: true, $or: [ { op: "command", "command.createIndexes": { $exists: true } }, { op: "none", "msg" : /^Index Build/ } ] } ) 결과 문서에서
inprog
필드 값이 빈 배열이면 진행 중인 인덱스 빌드는 없습니다.{ inprog: [], ok: 1, '$clusterTime': { ... }, operationTime: <timestamp> }
참고
리샤딩은 쓰기 집약적인 프로세스로 oplog 비율을 높일 수 있습니다. 다음을 수행할 수 있습니다.
고정된 oplog 크기를 설정하여 무한한 oplog 증가를 방지합니다.
하나 이상의 세컨더리 노드가 오래된 상태가 될 가능성을 최소화하기 위해 oplog 크기를 늘립니다.
자세한 내용은 복제본 세트 Oplog 문서를 참조하세요.
단계
컬렉션 리샤딩 작업에서 샤드는 다음과 같을 수 있습니다.
샤드는 기증자와 수신자가 동시에 될 수 있습니다. 구역을 사용하지 않는 한 기증자 샤드 세트는 수신자 샤드와 동일합니다.
config 서버 프라이머리는 항상 리샤딩 코디네이터이며 리샤딩 작업의 각 단계를 시작합니다.
리샤딩 작업을 시작합니다.
mongos
에 연결된 동안 리샤딩할 컬렉션과 새 샤드 키를 지정하는 reshardCollection
명령을 실행합니다.
db.adminCommand({ reshardCollection: "<database>.<collection>", key: <shardkey> })
MongoDB는 쓰기를 차단하는 최대 시간(초)을 2초로 설정하고 리샤딩 작업을 시작합니다.
리샤딩 작업을 모니터링합니다.
리샤딩 작업을 모니터링하려면 $currentOp
파이프라인 단계를 사용할 수 있습니다.
db.getSiblingDB("admin").aggregate([ { $currentOp: { allUsers: true, localOps: false } }, { $match: { type: "op", "originatingCommand.reshardCollection": "<database>.<collection>" } } ])
참고
업데이트된 값을 확인하려면 이전 파이프라인을 계속 실행해야 합니다.
$currentOp
파이프라인은 다음을 출력합니다.
totalOperationTimeElapsedSecs
: 경과된 작업 시간(초)remainingOperationTimeEstimatedSecs
: 현재 리샤딩 작업에 남은 예상 시간(초)입니다. 새로운 리샤딩 작업이 시작되면-1
(으)로 반환됩니다.시작 시간:
MongoDB 5.0 하지만 MongoDB 7.0 이전에는
remainingOperationTimeEstimatedSecs
를 리샤딩 작업 중에 수신자 샤드 에서만 사용할 수 있습니다.MongoDB 7.0
remainingOperationTimeEstimatedSecs
도 리샤딩 작업 중에 코디네이터에서 사용할 수 있습니다.
리샤딩 작업은 다음 단계를 순서대로 수행합니다.
복제 단계에서는 현재 수집 데이터를 복제합니다.
따라잡기 단계에서는 보류 중인 모든 쓰기 작업을 리샤딩된 컬렉션에 적용합니다.
remainingOperationTimeEstimatedSecs
비관치 추정으로 설정됩니다.따라잡기 단계 시간 추정은 상대적으로 긴 시간인 클론 단계 시간으로 설정됩니다.
실제로 보류 중인 쓰기 작업이 적은 경우 실제 따라잡기 단계 시간은 상대적으로 짧습니다.
[ { shard: '<shard>', type: 'op', desc: 'ReshardingRecipientService | ReshardingDonorService | ReshardingCoordinatorService <reshardingUUID>', op: 'command', ns: '<database>.<collection>', originatingCommand: { reshardCollection: '<database>.<collection>', key: <shardkey>, unique: <boolean>, collation: { locale: 'simple' } }, totalOperationTimeElapsedSecs: <number>, remainingOperationTimeEstimatedSecs: <number>, ... }, ... ]
리샤딩 작업을 완료합니다.
리샤딩 프로세스 전반에 걸쳐 리샤딩 작업 완료 예상 시간(remainingOperationTimeEstimatedSecs
)이(가) 줄어듭니다. 예상 시간이 2초 미만이면 MongoDB는 쓰기를 차단하고 리샤딩 작업을 완료합니다. 재공유 작업의 예상 완료 시간이 2초 미만이 될 때까지 리샤딩 작업은 기본적으로 쓰기를 차단하지 않습니다. 쓰기가 차단되는 기간 동안 애플리케이션의 대기 시간이 증가합니다.
리샤딩 프로세스가 완료되면 리샤딩 명령은 ok: 1
을(를) 반환합니다.
{ ok: 1, '$clusterTime': { clusterTime: <timestamp>, signature: { hash: Binary(Buffer.from("0000000000000000000000000000000000000000", "hex"), 0), keyId: <number> } }, operationTime: <timestamp> }
리샤딩 작업이 성공적으로 완료되었는지 확인하려면 sh.status()
메서드의 출력을 확인합니다.
sh.status()
sh.status()
메서드 출력에는 databases
하위 섹션이 포함됩니다. 리샤딩이 성공적으로 완료되면 출력에 컬렉션의 새 샤드 키가 나열됩니다.
databases [ { database: { _id: '<database>', primary: '<shard>', version: { uuid: <uuid>, timestamp: <timestamp>, lastMod: <number> } }, collections: { '<database>.<collection>': { shardKey: <shardkey>, unique: <boolean>, balancing: <boolean>, chunks: [], tags: [] } } } ... ]
참고
리샤딩된 컬렉션에서 Atlas Search를 사용하는 경우 리샤딩 작업이 완료되면 검색 인덱스를 사용할 수 없게 됩니다. 리샤딩 작업이 완료되면 검색 인덱스를 수동으로 다시 작성해야 합니다.
리샤딩을 완료하기 위해 쓰기를 조기에 차단
commitReshardCollection
명령을 실행하여 리샤딩 작업을 수동으로 강제로 완료할 수 있습니다. 이는 리샤딩 작업을 완료하는 데 걸리는 현재 예상 시간이 컬렉션 에서 쓰기를 차단 하기에 적합한 기간인 경우에 유용합니다. commitReshardCollection
명령은 중요 섹션의 기간 동안 쓰기를 차단하고 리샤딩 작업을 강제로 완료합니다. 명령의 구문은 다음과 같습니다.
db.adminCommand({ commitReshardCollection: "<database>.<collection>" })
리샤딩 작업 중단
commitReshardCollection
을(를) 실행 후에도 리샤딩 작업의 모든 단계에서 샤드가 완전히 따라잡을 때까지 리샤딩 작업을 중단할 수 있습니다.
예를 예시 remainingOperationTimeEstimatedSecs
이 감소하지 않으면 abortReshardCollection
명령을 사용하여 리샤딩 작업을 중단할 수 있습니다.
db.adminCommand({ abortReshardCollection: "<database>.<collection>" })
작업을 취소한 후 쓰기 볼륨이 적은 기간 동안 리샤딩 작업을 다시 시도할 수 있습니다. 이것이 불가능하다면 샤드를 더 추가 한 후 다시 시도합니다.
행동
리샤딩 작업의 최소 지속 시간
리샤딩 작업의 최소 기간은 항상 5분입니다.
재시도 가능한 쓰기
리샤딩 이전이나 도중에 시작된 재시도 가능 쓰기는 컬렉션이 리샤딩되는 동안과 이후에 최대 5분 동안 재시도될 수 있습니다. 5분 후에 쓰기의 최종 결과를 찾지 못할 수 있으며 이후 쓰기 재시도가 IncompleteTransactionHistory
오류와 함께 실패할 수 있습니다.
오류 사례
Duplicate _id
Values
컬렉션 데이터 손상을 방지하기 위해 _id
값이 전체적으로 고유하지 않으면 리샤딩 작업이 실패합니다. 중복 _id
값은 성공적인 청크 마이그레이션을 방해할 수도 있습니다. 중복 _id
값이 있는 문서가 있는 경우 각 문서의 데이터를 새 문서로 복사한 다음 중복 문서를 삭제하십시오.