Abfragen mit Bereichs- und Ungleichheitsfiltern für mehrere Felder optimieren
Auf dieser Seite finden Sie Beispiele für Indexierungsstrategien, die Sie für Abfragen mit Bereichs- und Ungleichheitsfiltern auf mehreren Feldern verwenden können, um Abfragen effizienter zu gestalten.
Bevor Sie Ihre Abfragen optimieren, sollten Sie sich über verwandte Konzepte informieren.
Abfragen mit Query Explain optimieren
Um festzustellen, ob Ihre Abfrage und Indexe optimal sind, können Sie Query Erklären, um die Zusammenfassung des Abfrageplans und die Ausführungsstatistiken zu erhalten der Abfrage:
Java
Query q = db.collection("employees").whereGreaterThan("salary",
100000).whereGreaterThan("experience", 0);
ExplainResults<QuerySnapshot> explainResults = q.explain(ExplainOptions.builder().analyze(true).build()).get();
ExplainMetrics metrics = explainResults.getMetrics();
PlanSummary planSummary = metrics.getPlanSummary();
ExecutionStats executionStats = metrics.getExecutionStats();
System.out.println(planSummary.getIndexesUsed());
System.out.println(stats.getResultsReturned());
System.out.println(stats.getExecutionDuration());
System.out.println(stats.getReadOperations());
System.out.println(stats.getDebugStats());
Node.js
let q = db.collection("employees")
.where("salary", ">", 100000)
.where("experience", ">",0);
let options = { analyze : 'true' };
let explainResults = await q.explain(options);
let planSummary = explainResults.metrics.planSummary;
let stats = explainResults.metrics.executionStats;
console.log(planSummary);
console.log(stats);
Das folgende Beispiel zeigt, wie bei korrekter Indexreihenfolge der Anzahl der Indexeinträge, die von Firestore gescannt werden.
Einfache Abfragen
Beim früheren Beispiel einer Mitarbeitersammlung würde die einfache Abfrage
der mit dem Index (experience ASC, salary ASC)
ausgeführt wird:
Java
db.collection("employees")
.whereGreaterThan("salary", 100000)
.whereGreaterThan("experience", 0)
.orderBy("experience")
.orderBy("salary");
Die Abfrage scannt 95.000 Indexeinträge, um nur fünf Dokumente zurückzugeben. Da die Abfrage nicht erfüllt ist, wird eine große Anzahl von Indexeinträgen gelesen, herausgefiltert.
// Output query planning info { "indexesUsed": [ { "properties": "(experience ASC, salary ASC, __name__ ASC)", "query_scope": "Collection" } ], // Output Query Execution Stats "resultsReturned": "5", "executionDuration": "2.5s", "readOperations": "100", "debugStats": { "index_entries_scanned": "95000", "documents_scanned": "5", "billing_details": { "documents_billable": "5", "index_entries_billable": "95000", "small_ops": "0", "min_query_cost": "0" } } }
Sie können aus dem Domänenwissen ableiten, dass die meisten Mitarbeitenden mindestens
aber nur wenige haben ein Gehalt von mehr als 100.000. Anhand dieser Informationen sehen Sie, dass die Einschränkung salary
selektiver ist als die Einschränkung experience
. Um den Index zu beeinflussen, den Firestore für die
die Abfrage ausführen und dabei eine orderBy
-Klausel angeben, die die salary
vor der experience
-Einschränkung.
Java
db.collection("employees")
.whereGreaterThan("salary", 100000)
.whereGreaterThan("experience", 0)
.orderBy("salary")
.orderBy("experience");
Wenn Sie die Prädikate explizit mit der orderBy()
-Klausel hinzufügen,
Firestore verwendet den Index (salary ASC, experience ASC)
, um die Abfrage auszuführen.
Da die Selektivität des ersten Bereichsfilters in dieser Abfrage im Vergleich zur vorherigen Abfrage höher ist, wird sie schneller ausgeführt und ist kosteneffizienter.
// Output query planning info { "indexesUsed": [ { "properties": "(salary ASC, experience ASC, __name__ ASC)", "query_scope": "Collection" } ], // Output Query Execution Stats "resultsReturned": "5", "executionDuration": "0.2s", "readOperations": "6", "debugStats": { "index_entries_scanned": "1000", "documents_scanned": "5", "billing_details": { "documents_billable": "5", "index_entries_billable": "1000", "small_ops": "0", "min_query_cost": "0" } } }
Nächste Schritte
- Weitere Informationen zu Query Explain
- Weitere Informationen zu Best Practices für die Indexierung