분할된 필드로 최적화된 쿼리
이 페이지에서는 Firestore에서 분할된 필드의 사용량을 보고 제어하는 방법을 설명합니다. 이 기능은 Firestore Enterprise 버전에서 사용할 수 있습니다.
문서가 작성되면 Firestore는 특정 필드를 분할된 형식으로 저장해야 한다고 판단할 수 있습니다. 분할된 필드는 전체 문서 대신 필요한 필드만 읽어 쿼리 성능을 최적화합니다.
분할된 필드의 이점을 활용하는 쿼리
분할된 필드에 대한 읽기는 해당하는 경우 다음 쿼리 형태에 적용됩니다.
집계 쿼리: 집계 작업을 위해 필드의 하위 집합에만 액세스해야 하는 쿼리입니다. 예를 들면 다음과 같습니다.
db.pipeline() .collection("/customers") .where(lessThan("account_balance", 0)) .aggregate( countAll().as("total"), )또는 group-by를 사용합니다.
db.pipeline() .collection("/customers") .where(lessThan("account_balance", 0)) .aggregate({ accumulators: [ field('account_balance').average().as('avg_account_balance') ], groups: [field('market_segment')] })프로젝션 쿼리: 필드의 특정 하위 집합만 반환하는 쿼리입니다. 예를 들면 다음과 같습니다.
db.pipeline() .collection("/customers") .select("family_name", "given_name") .limit(10)필터 쿼리: Firestore 쿼리 엔진이 문서 필터링에 분할된 필드를 사용하는 것이 유익하다고 판단하는 쿼리입니다. 예를 들면 다음과 같습니다.
db.pipeline() .collection("/customers") .where(equal("given_name", "alice"))
분할된 필드 사용량 보기
쿼리 설명을 사용하여 쿼리가 분할된 필드를 사용하는지 확인할 수 있습니다. 쿼리 계획의 TableScan 노드에는 다음 측정항목이 포함된 Storage 섹션이 포함되어 있습니다.
- 스캔 형태:
shredded_fields_only: 쿼리가 분할된 필드에서만 읽습니다.shredded_fields_backjoin: 쿼리가 분할된 필드에서 읽고 다른 필드의 원본 문서와 조인합니다.
- 사용된 분할된 필드: 분할된 필드로 읽은 필드 이름 목록입니다.
- 재확인 횟수: 재확인 카운터의 맵입니다. 재확인은 분할된 필드를 스캔할 때 원래 전체 문서에서 읽기로 되돌아가는 것을 의미합니다. 문서의 필드 값이 8KiB를 초과하는 경우 발생할 수 있습니다. 이는 분할된 필드 저장소에 비해 너무 큽니다.
출력 예
...
└── • TableScan
source: /customers
order: UNDEFINED
row range: (-∞..+∞)
filter: ($account_balance_1 < 0L)
output bindings: {$account_balance_1=account_balance, $market_segment_1=market_segment}
variables: [$account_balance_1, $market_segment_1]
Execution:
records returned: 1,374
latency: 26.58 ms
post-filtered rows: 13,626
records scanned: 15,000
data bytes read: 23.73 MiB (24,887,141 B)
Storage:
scan shape: shredded_fields_only
shredded fields used: [account_balance, market_segment]
분할된 필드 사용량 제어
기본적으로 Firestore는 분할된 필드를 사용할 수 있는 경우 이를 사용합니다. table_scan_method 쿼리 옵션을 사용하여 이 동작을 제어할 수 있습니다.
table_scan_method 옵션에 지원되는 값은 다음과 같습니다.
shredded_fields_enabled(기본값): 분할된 필드를 사용할 수 있는 경우 이를 사용합니다.shredded_fields_disabled: 분할된 필드를 사용하지 않습니다.force_shredded_fields: 분할된 필드를 스캔하여 테이블 스캔을 완료할 수 없는 경우 쿼리가 실패합니다.
예
var opts = new PipelineExecuteOptions()
.with("table_scan_method", "shredded_fields_disabled");
var snapshot = db.pipeline()
.collection("/customers")
.where(equal("given_name", "alice"))
.execute(opts)
.get();
쿼리 성능 경고
Firestore는 비효율적인 분할된 필드 사용이 감지되면 쿼리 설명 결과에 성능 경고를 표시할 수 있습니다. 예를 들면 다음과 같습니다.
선별성이 낮은 쿼리: 쿼리가 필터링을 위해 분할된 필드를 스캔하지만 필터링되는 문서가 너무 적어 스캔이 비효율적인 경우 발생합니다.
재확인 횟수가 많은 쿼리: 쿼리가 전체 문서 읽기로 자주 되돌아가 성능에 영향을 미칠 수 있는 경우 발생합니다.
storage_size와 같은 함수를 사용하여 재확인을 트리거하는 큰 값을 식별할 수 있습니다.
이러한 경우 쿼리 옵션을 사용하여 분할된 필드 읽기를 사용 중지하는 것이 좋습니다.
제한사항
Firestore는 최상위 필드만 분할합니다. 또한 컬렉션 그룹당 분할할 수 있는 필드 수를 제한합니다.