use of com.apple.foundationdb.record.RecordCoreException in project fdb-record-layer by FoundationDB.
the class UnionVisitor method postVisit.
@Nonnull
@Override
public RecordQueryPlan postVisit(@Nonnull final RecordQueryPlan recordQueryPlan) {
if (recordQueryPlan instanceof RecordQueryUnionPlanBase) {
RecordQueryUnionPlanBase unionPlan = (RecordQueryUnionPlanBase) recordQueryPlan;
final Set<KeyExpression> requiredFields = unionPlan.getRequiredFields();
boolean shouldPullOutFilter = false;
QueryComponent filter = null;
if (unionPlan.getChildren().stream().allMatch(child -> child instanceof RecordQueryFilterPlan)) {
filter = ((RecordQueryFilterPlan) unionPlan.getChildren().get(0)).getConjunctedFilter();
// needed for lambda expression
final QueryComponent finalFilter = filter;
shouldPullOutFilter = unionPlan.getChildren().stream().allMatch(plan -> ((RecordQueryFilterPlan) plan).getConjunctedFilter().equals(finalFilter));
}
List<ExpressionRef<RecordQueryPlan>> newChildren = new ArrayList<>(unionPlan.getChildren().size());
for (RecordQueryPlan plan : unionPlan.getChildren()) {
if (shouldPullOutFilter) {
// Check if the plan under the filter can have its index fetch removed.
if (!(plan instanceof RecordQueryFilterPlan)) {
throw new RecordCoreException("serious logic error: thought this was a filter plan but it wasn't");
}
plan = ((RecordQueryFilterPlan) plan).getChild();
}
@Nullable RecordQueryPlan newPlan = removeIndexFetch(plan, requiredFields);
if (newPlan == null) {
// can't remove index fetch, so give up
return recordQueryPlan;
}
newChildren.add(GroupExpressionRef.of(newPlan));
}
RecordQueryPlan newUnionPlan = new RecordQueryFetchFromPartialRecordPlan(unionPlan.withChildrenReferences(newChildren), TranslateValueFunction.unableToTranslate());
if (shouldPullOutFilter) {
return new RecordQueryFilterPlan(newUnionPlan, filter);
} else {
return newUnionPlan;
}
}
return recordQueryPlan;
}
use of com.apple.foundationdb.record.RecordCoreException in project fdb-record-layer by FoundationDB.
the class QueryPredicate method findImpliedMappings.
/**
* Method to find all mappings of this predicate in an {@link Iterable} of candidate predicates. If no mapping can
* be found at all, this method will then call {@link #impliesCandidatePredicate(AliasMap, QueryPredicate)} using
* a tautology predicate as candidate which should by contract should return a {@link PredicateMapping}.
* @param aliasMap the current alias map
* @param candidatePredicates an {@link Iterable} of candiate predicates
* @return a non-empty set of {@link PredicateMapping}s
*/
default Set<PredicateMapping> findImpliedMappings(@NonNull AliasMap aliasMap, @Nonnull Iterable<? extends QueryPredicate> candidatePredicates) {
final ImmutableSet.Builder<PredicateMapping> mappingBuilder = ImmutableSet.builder();
for (final QueryPredicate candidatePredicate : candidatePredicates) {
final Optional<PredicateMapping> impliedByQueryPredicateOptional = impliesCandidatePredicate(aliasMap, candidatePredicate);
impliedByQueryPredicateOptional.ifPresent(mappingBuilder::add);
}
final ImmutableSet<PredicateMapping> result = mappingBuilder.build();
if (result.isEmpty()) {
final ConstantPredicate tautologyPredicate = new ConstantPredicate(true);
return impliesCandidatePredicate(aliasMap, tautologyPredicate).map(ImmutableSet::of).orElseThrow(() -> new RecordCoreException("should have found at least one mapping"));
}
return result;
}
use of com.apple.foundationdb.record.RecordCoreException in project fdb-record-layer by FoundationDB.
the class FDBRecordStoreScanLimitTest method assertNumberOfRecordsScanned.
private void assertNumberOfRecordsScanned(int expected, Function<byte[], RecordCursor<FDBQueriedRecord<Message>>> cursorFunction, boolean failOnLimitReached, String message) throws Exception {
try (FDBRecordContext context = openContext()) {
openSimpleRecordStore(context);
if (context.getTimer() != null) {
context.getTimer().reset();
}
try (RecordCursor<FDBQueriedRecord<Message>> cursor = cursorFunction.apply(null)) {
boolean caughtScanLimitReached = false;
RecordCursorResult<FDBQueriedRecord<Message>> result = null;
try {
do {
result = cursor.getNext();
} while (result.hasNext());
} catch (RecordCoreException ex) {
if (failOnLimitReached && ex.getCause() instanceof ScanLimitReachedException) {
caughtScanLimitReached = true;
} else {
throw ex;
}
}
if (failOnLimitReached && !caughtScanLimitReached) {
assertNotEquals(RecordCursor.NoNextReason.SCAN_LIMIT_REACHED, result.getNoNextReason());
}
Optional<Integer> scanned = getRecordScanned(context);
if (context.getTimer() != null) {
context.getTimer().reset();
}
int overrun = BaseCursorCountVisitor.getCount(cursor);
scanned.ifPresent(value -> assertThat(message, value, lessThanOrEqualTo(expected + overrun)));
}
}
}
use of com.apple.foundationdb.record.RecordCoreException in project fdb-record-layer by FoundationDB.
the class DualPlannerExtension method provideTestTemplateInvocationContexts.
@Override
public Stream<TestTemplateInvocationContext> provideTestTemplateInvocationContexts(ExtensionContext context) {
final String displayName = context.getDisplayName();
if (AnnotationUtils.isAnnotated(context.getTestMethod(), ParameterizedTest.class)) {
TestTemplateInvocationContextProvider nestedProvider;
try {
Constructor<?> nestedProviderConstructor = Class.forName("org.junit.jupiter.params.ParameterizedTestExtension").getDeclaredConstructor();
nestedProviderConstructor.setAccessible(true);
nestedProvider = (TestTemplateInvocationContextProvider) nestedProviderConstructor.newInstance();
} catch (ClassNotFoundException | NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException e) {
throw new RecordCoreException(e.getClass() + " " + e.getMessage());
}
return nestedProvider.provideTestTemplateInvocationContexts(context).map(existingContext -> new DualPlannerTestInvocationContext(displayName, true, existingContext.getAdditionalExtensions()));
} else {
return Stream.of(// old planner
new DualPlannerTestInvocationContext(displayName, false), // new planner
new DualPlannerTestInvocationContext(displayName, true));
}
}
use of com.apple.foundationdb.record.RecordCoreException in project fdb-record-layer by FoundationDB.
the class FDBDirectory method readBlock.
/**
* Reads known data from the directory.
* @param resourceDescription Description should be non-null, opaque string describing this resource; used for logging
* @param referenceFuture the reference where the data supposedly lives
* @param block the block where the data is stored
* @return Completable future of the data returned
* @throws RecordCoreException if blockCache fails to get the data from the block
* @throws RecordCoreArgumentException if a reference with that id hasn't been written yet.
*/
// checks and throws more relevant exception
@SuppressWarnings("PMD.UnusedNullCheckInEquals")
@Nonnull
public CompletableFuture<byte[]> readBlock(@Nonnull String resourceDescription, @Nonnull CompletableFuture<FDBLuceneFileReference> referenceFuture, int block) throws RecordCoreException {
try {
if (LOGGER.isTraceEnabled()) {
LOGGER.trace(getLogMessage("readBlock", LogMessageKeys.FILE_NAME, resourceDescription, LogMessageKeys.BLOCK_NUMBER, block));
}
// Tried to fully pipeline this but the reality is that this is mostly cached after listAll, delete, etc.
final FDBLuceneFileReference reference = referenceFuture.join();
if (reference == null) {
throw new RecordCoreArgumentException(String.format("No reference with name %s was found", resourceDescription));
}
Long id = reference.getId();
long start = System.nanoTime();
return context.instrument(FDBStoreTimer.Events.LUCENE_READ_BLOCK, blockCache.get(Pair.of(id, block), () -> context.instrument(FDBStoreTimer.Events.LUCENE_FDB_READ_BLOCK, context.ensureActive().get(dataSubspace.pack(Tuple.from(id, block))).thenApplyAsync(data -> LuceneSerializer.decode(data)))), start);
} catch (ExecutionException e) {
throw new RecordCoreException(CompletionExceptionLogHelper.asCause(e));
}
}
Aggregations