use of com.apple.foundationdb.record.query.plan.plans.RecordQueryTextIndexPlan in project fdb-record-layer by FoundationDB.
the class RecordQueryPlanner method planText.
@Nullable
private ScoredPlan planText(@Nonnull CandidateScan candidateScan, @Nonnull Index index, @Nonnull QueryComponent filter, @Nullable KeyExpression sort) {
if (sort != null) {
// TODO: Full Text: Sorts are not supported with full text queries (https://github.com/FoundationDB/fdb-record-layer/issues/55)
return null;
}
FilterSatisfiedMask filterMask = FilterSatisfiedMask.of(filter);
final TextScan scan = TextScanPlanner.getScanForQuery(index, filter, false, filterMask);
if (scan == null) {
return null;
}
// TODO: Check the rest of the fields of the text index expression to see if the sort and unsatisfied filters can be helped.
RecordQueryPlan plan = new RecordQueryTextIndexPlan(index.getName(), scan, candidateScan.reverse);
// Add a type filter if the index is over more types than those the query specifies
Set<String> possibleTypes = getPossibleTypes(index);
plan = addTypeFilterIfNeeded(candidateScan, plan, possibleTypes);
// is "strict", it must be surrounded be a filter plan.
if (scan.getTextComparison() instanceof Comparisons.TextContainsAllPrefixesComparison) {
Comparisons.TextContainsAllPrefixesComparison textComparison = (Comparisons.TextContainsAllPrefixesComparison) scan.getTextComparison();
if (textComparison.isStrict()) {
plan = new RecordQueryFilterPlan(plan, filter);
filterMask.setSatisfied(true);
}
}
// than other indexes.
return new ScoredPlan(plan, filterMask.getUnsatisfiedFilters(), Collections.emptyList(), 10, scan.createsDuplicates(), null);
}
use of com.apple.foundationdb.record.query.plan.plans.RecordQueryTextIndexPlan in project fdb-record-layer by FoundationDB.
the class PlanOrderingKey method forPlan.
@Nullable
public static PlanOrderingKey forPlan(@Nonnull RecordMetaData metaData, @Nonnull RecordQueryPlan queryPlan, @Nullable KeyExpression primaryKey) {
if (primaryKey == null) {
return null;
}
while (queryPlan instanceof RecordQueryFilterPlan) {
queryPlan = ((RecordQueryFilterPlan) queryPlan).getInnerPlan();
}
if (queryPlan instanceof RecordQueryPlanWithIndex) {
final RecordQueryPlanWithIndex indexPlan = (RecordQueryPlanWithIndex) queryPlan;
final Index index = metaData.getIndex(indexPlan.getIndexName());
final List<KeyExpression> keys = new ArrayList<>(index.getRootExpression().normalizeKeyForPositions());
int pkeyStart = keys.size();
int pKeyTail = pkeyStart;
// Primary keys come after index value keys, unless they were already part of it.
for (KeyExpression pkey : primaryKey.normalizeKeyForPositions()) {
int pos = keys.indexOf(pkey);
if (pos < 0) {
keys.add(pkey);
} else if (pkeyStart > pos) {
pkeyStart = pos;
}
}
final int prefixSize;
if (indexPlan instanceof RecordQueryIndexPlan) {
prefixSize = ((RecordQueryIndexPlan) indexPlan).getComparisons().getEqualitySize();
} else if (indexPlan instanceof RecordQueryTextIndexPlan) {
final TextScan textScan = ((RecordQueryTextIndexPlan) indexPlan).getTextScan();
int groupingSize = textScan.getGroupingComparisons() != null ? textScan.getGroupingComparisons().getEqualitySize() : 0;
int suffixSize = textScan.getSuffixComparisons() != null ? textScan.getSuffixComparisons().getEqualitySize() : 0;
if (textScan.getTextComparison().getType().isEquality()) {
// Can use the equality comparisons in the grouping columns and any columns after the text index
// plus the text column itself.
prefixSize = groupingSize + suffixSize + 1;
} else {
// by the token that the prefix scan just so happened to hit.
return null;
}
} else {
// Some unknown index plan. Maybe this should throw an error?
return null;
}
return new PlanOrderingKey(keys, prefixSize, pkeyStart, pKeyTail);
} else if (queryPlan instanceof RecordQueryScanPlan) {
final RecordQueryScanPlan scanPlan = (RecordQueryScanPlan) queryPlan;
return new PlanOrderingKey(primaryKey.normalizeKeyForPositions(), scanPlan.getComparisons().getEqualitySize(), 0, 0);
} else if (queryPlan instanceof RecordQueryIntersectionPlan) {
return forComparisonKey(((RecordQueryIntersectionPlan) queryPlan).getComparisonKey(), primaryKey);
} else if (queryPlan instanceof RecordQueryUnionPlan) {
return forComparisonKey(((RecordQueryUnionPlan) queryPlan).getComparisonKey(), primaryKey);
} else {
return null;
}
}
Aggregations