use of com.apple.foundationdb.record.query.plan.sorting.RecordQueryPlannerSortConfiguration in project fdb-record-layer by FoundationDB.
the class RecordQueryPlanner method plan.
/**
* Create a plan to get the results of the provided query.
*
* @param query a query for records on this planner's metadata
* @param parameterRelationshipGraph a set of bindings and their relationships that provide additional information
* to the planner that may improve plan quality but may also tighten requirements imposed on the parameter
* bindings that are used to execute the query
* @return a plan that will return the results of the provided query when executed
* @throws com.apple.foundationdb.record.RecordCoreException if there is no index that matches the sort in the provided query
*/
@Nonnull
@Override
public RecordQueryPlan plan(@Nonnull RecordQuery query, @Nonnull ParameterRelationshipGraph parameterRelationshipGraph) {
query.validate(metaData);
final PlanContext planContext = getPlanContext(query);
final BooleanNormalizer normalizer = BooleanNormalizer.forConfiguration(configuration);
final QueryComponent queryFilter = query.getFilter();
final QueryComponent filter = normalizer.normalizeIfPossible(queryFilter == null ? null : queryFilter.withParameterRelationshipMap(parameterRelationshipGraph));
final KeyExpression sort = query.getSort();
final boolean sortReverse = query.isSortReverse();
RecordQueryPlan plan = plan(planContext, filter, sort, sortReverse);
if (plan == null) {
if (sort == null) {
throw new RecordCoreException("Unexpected failure to plan without sort");
}
final RecordQueryPlannerSortConfiguration sortConfiguration = configuration.getSortConfiguration();
if (sortConfiguration != null && sortConfiguration.shouldAllowNonIndexSort(query)) {
final PlanContext withoutSort = new PlanContext(query.toBuilder().setSort(null).build(), planContext.indexes, planContext.commonPrimaryKey);
plan = plan(withoutSort, filter, null, false);
if (plan == null) {
throw new RecordCoreException("Unexpected failure to plan without sort");
}
plan = new RecordQuerySortPlan(plan, sortConfiguration.getSortKey(sort, sortReverse));
} else {
throw new RecordCoreException("Cannot sort without appropriate index: " + sort);
}
}
if (query.getRequiredResults() != null) {
plan = tryToConvertToCoveringPlan(planContext, plan);
}
if (timer != null) {
plan.logPlanStructure(timer);
}
if (plan.getComplexity() > configuration.getComplexityThreshold()) {
throw new RecordQueryPlanComplexityException(plan);
}
if (logger.isTraceEnabled()) {
logger.trace(KeyValueLogMessage.of("explain of plan", "explain", PlannerGraphProperty.explain(plan)));
}
return plan;
}
Aggregations