use of com.apple.test.BooleanSource in project fdb-record-layer by FoundationDB.
the class FDBOrQueryToUnionTest method testOrQueryChildReordering2.
@DualPlannerTest
@ParameterizedTest
@BooleanSource
void testOrQueryChildReordering2(boolean shouldDeferFetch) throws Exception {
RecordMetaDataHook hook = complexQuerySetupHook();
complexQuerySetup(hook);
RecordQuery query1 = RecordQuery.newBuilder().setRecordType("MySimpleRecord").setFilter(Query.or(Query.field("str_value_indexed").equalsValue("odd"), Query.field("num_value_3_indexed").equalsValue(0), Query.field("num_value_3_indexed").equalsValue(3))).setSort(null, true).setRemoveDuplicates(true).build();
setDeferFetchAfterUnionAndIntersection(shouldDeferFetch);
// Index(MySimpleRecord$str_value_indexed [[odd],[odd]] REVERSE) ∪ Index(MySimpleRecord$num_value_3_indexed [[0],[0]] REVERSE) ∪ Index(MySimpleRecord$num_value_3_indexed [[3],[3]] REVERSE)
// Fetch(Covering(Index(MySimpleRecord$str_value_indexed [[odd],[odd]] REVERSE) -> [rec_no: KEY[1], str_value_indexed: KEY[0]]) ∪ Covering(Index(MySimpleRecord$num_value_3_indexed [[0],[0]] REVERSE) -> [num_value_3_indexed: KEY[0], rec_no: KEY[1]]) ∪ Covering(Index(MySimpleRecord$num_value_3_indexed [[3],[3]] REVERSE) -> [num_value_3_indexed: KEY[0], rec_no: KEY[1]]))
RecordQueryPlan plan1 = planner.plan(query1);
RecordQuery query2 = query1.toBuilder().setFilter(Query.or(Lists.reverse(Objects.requireNonNull((OrComponent) query1.getFilter()).getChildren()))).build();
// Index(MySimpleRecord$num_value_3_indexed [[3],[3]] REVERSE) ∪ Index(MySimpleRecord$num_value_3_indexed [[0],[0]] REVERSE) ∪ Index(MySimpleRecord$str_value_indexed [[odd],[odd]] REVERSE)
// Fetch(Covering(Index(MySimpleRecord$num_value_3_indexed [[3],[3]] REVERSE) -> [num_value_3_indexed: KEY[0], rec_no: KEY[1]]) ∪ Covering(Index(MySimpleRecord$num_value_3_indexed [[0],[0]] REVERSE) -> [num_value_3_indexed: KEY[0], rec_no: KEY[1]]) ∪ Covering(Index(MySimpleRecord$str_value_indexed [[odd],[odd]] REVERSE) -> [rec_no: KEY[1], str_value_indexed: KEY[0]]))
RecordQueryPlan plan2 = planner.plan(query2);
assertNotEquals(plan1.hashCode(), plan2.hashCode());
assertNotEquals(plan1, plan2);
assertEquals(plan1.semanticHashCode(), plan2.semanticHashCode());
assertTrue(plan1.semanticEquals(plan2));
if (shouldDeferFetch || planner instanceof CascadesPlanner) {
assertEquals(770691035, plan1.planHash(PlanHashable.PlanHashKind.LEGACY));
assertEquals(1890796442, plan1.planHash(PlanHashable.PlanHashKind.FOR_CONTINUATION));
assertEquals(55660884, plan1.planHash(PlanHashable.PlanHashKind.STRUCTURAL_WITHOUT_LITERALS));
assertEquals(1289607451, plan2.planHash(PlanHashable.PlanHashKind.LEGACY));
assertEquals(-29394342, plan2.planHash(PlanHashable.PlanHashKind.FOR_CONTINUATION));
assertEquals(1772831508, plan2.planHash(PlanHashable.PlanHashKind.STRUCTURAL_WITHOUT_LITERALS));
} else {
assertEquals(723665474, plan1.planHash(PlanHashable.PlanHashKind.LEGACY));
assertEquals(-330673401, plan1.planHash(PlanHashable.PlanHashKind.FOR_CONTINUATION));
assertEquals(2129158337, plan1.planHash(PlanHashable.PlanHashKind.STRUCTURAL_WITHOUT_LITERALS));
assertEquals(184229634, plan2.planHash(PlanHashable.PlanHashKind.LEGACY));
assertEquals(2044103111, plan2.planHash(PlanHashable.PlanHashKind.FOR_CONTINUATION));
assertEquals(-448638335, plan2.planHash(PlanHashable.PlanHashKind.STRUCTURAL_WITHOUT_LITERALS));
}
Set<Long> seen = new HashSet<>();
try (FDBRecordContext context = openContext()) {
openSimpleRecordStore(context, hook);
int i = 0;
try (RecordCursorIterator<FDBQueriedRecord<Message>> cursor1 = recordStore.executeQuery(plan1).asIterator();
RecordCursorIterator<FDBQueriedRecord<Message>> cursor2 = recordStore.executeQuery(plan2).asIterator()) {
while (cursor1.hasNext()) {
assertThat(cursor2.hasNext(), is(true));
FDBQueriedRecord<Message> rec1 = cursor1.next();
FDBQueriedRecord<Message> rec2 = cursor2.next();
assertEquals(Objects.requireNonNull(rec1).getRecord(), Objects.requireNonNull(rec2).getRecord());
TestRecords1Proto.MySimpleRecord.Builder myrec = TestRecords1Proto.MySimpleRecord.newBuilder();
myrec.mergeFrom(rec1.getRecord());
assertTrue(myrec.getStrValueIndexed().equals("odd") || myrec.getNumValue3Indexed() == 0 || myrec.getNumValue3Indexed() == 3, "condition on record not met");
assertFalse(seen.contains(myrec.getRecNo()), "Already saw a record!");
seen.add(myrec.getRecNo());
i++;
}
assertThat(cursor2.hasNext(), is(false));
}
assertEquals(70, i);
assertDiscardedAtMost(40, context);
if (shouldDeferFetch) {
assertLoadRecord(140, context);
}
}
}
use of com.apple.test.BooleanSource in project fdb-record-layer by FoundationDB.
the class FDBOrQueryToUnionTest method testComplexLimits5.
/**
* Verify that an OR on two indexed fields with compatibly ordered indexes is implemented by a union, and that the
* union cursors works properly with a returned record limit.
*/
@DualPlannerTest
@ParameterizedTest
@BooleanSource
void testComplexLimits5(boolean shouldDeferFetch) throws Exception {
RecordMetaDataHook hook = complexQuerySetupHook();
complexQuerySetup(hook);
RecordQuery query = RecordQuery.newBuilder().setRecordType("MySimpleRecord").setFilter(Query.or(Query.field("str_value_indexed").equalsValue("odd"), Query.field("num_value_3_indexed").equalsValue(0))).build();
setDeferFetchAfterUnionAndIntersection(shouldDeferFetch);
// Fetch(Covering(Index(MySimpleRecord$str_value_indexed [[odd],[odd]]) -> [rec_no: KEY[1], str_value_indexed: KEY[0]]) ∪ Covering(Index(MySimpleRecord$num_value_3_indexed [[0],[0]]) -> [num_value_3_indexed: KEY[0], rec_no: KEY[1]]))
RecordQueryPlan plan = planner.plan(query);
if (shouldDeferFetch || planner instanceof CascadesPlanner) {
final BindingMatcher<? extends RecordQueryPlan> planMatcher = fetchFromPartialRecordPlan(unionPlan(coveringIndexPlan().where(indexPlanOf(indexPlan().where(indexName("MySimpleRecord$str_value_indexed")).and(scanComparisons(range("[[odd],[odd]]"))))), coveringIndexPlan().where(indexPlanOf(indexPlan().where(indexName("MySimpleRecord$num_value_3_indexed")).and(scanComparisons(range("[[0],[0]]")))))).where(comparisonKey(primaryKey("MySimpleRecord"))));
assertMatchesExactly(plan, planMatcher);
assertEquals(-1584186334, plan.planHash(PlanHashable.PlanHashKind.LEGACY));
assertEquals(-351348461, plan.planHash(PlanHashable.PlanHashKind.FOR_CONTINUATION));
assertEquals(969743396, plan.planHash(PlanHashable.PlanHashKind.STRUCTURAL_WITHOUT_LITERALS));
} else {
final BindingMatcher<? extends RecordQueryPlan> planMatcher = unionPlan(indexPlan().where(indexName("MySimpleRecord$str_value_indexed")).and(scanComparisons(range("[[odd],[odd]]"))), indexPlan().where(indexName("MySimpleRecord$num_value_3_indexed")).and(scanComparisons(range("[[0],[0]]")))).where(comparisonKey(primaryKey("MySimpleRecord")));
assertMatchesExactly(plan, planMatcher);
assertEquals(-2067012605, plan.planHash(PlanHashable.PlanHashKind.LEGACY));
assertEquals(1790078012, plan.planHash(PlanHashable.PlanHashKind.FOR_CONTINUATION));
assertEquals(-1183797427, plan.planHash(PlanHashable.PlanHashKind.STRUCTURAL_WITHOUT_LITERALS));
}
try (FDBRecordContext context = openContext()) {
openSimpleRecordStore(context, hook);
int i = 0;
try (RecordCursorIterator<FDBQueriedRecord<Message>> cursor = recordStore.executeQuery(plan, null, ExecuteProperties.newBuilder().setReturnedRowLimit(5).build()).asIterator()) {
while (cursor.hasNext()) {
FDBQueriedRecord<Message> rec = cursor.next();
TestRecords1Proto.MySimpleRecord.Builder myrec = TestRecords1Proto.MySimpleRecord.newBuilder();
myrec.mergeFrom(Objects.requireNonNull(rec).getRecord());
if (myrec.getNumValue3Indexed() != 0) {
assertEquals("odd", myrec.getStrValueIndexed());
}
i += 1;
}
}
assertEquals(5, i);
assertDiscardedAtMost(1, context);
if (shouldDeferFetch) {
assertLoadRecord(5, context);
}
}
}
use of com.apple.test.BooleanSource in project fdb-record-layer by FoundationDB.
the class FDBOrQueryToUnionTest method testOrQuery3.
/**
* Verify that queries with an OR of non-overlapping range inequalities on the same field are implemented using a union
* of indexes.
*/
@DualPlannerTest
@ParameterizedTest
@BooleanSource
void testOrQuery3(boolean shouldDeferFetch) throws Exception {
RecordMetaDataHook hook = complexQuerySetupHook();
complexQuerySetup(hook);
RecordQuery query = RecordQuery.newBuilder().setRecordType("MySimpleRecord").setFilter(Query.or(Query.field("num_value_3_indexed").lessThan(2), Query.field("num_value_3_indexed").greaterThan(3))).build();
setDeferFetchAfterUnionAndIntersection(shouldDeferFetch);
// Fetch(Covering(Index(MySimpleRecord$num_value_3_indexed ([null],[2])) -> [num_value_3_indexed: KEY[0], rec_no: KEY[1]]) ∪[Field { 'num_value_3_indexed' None}, Field { 'rec_no' None}] Covering(Index(MySimpleRecord$num_value_3_indexed ([3],>) -> [num_value_3_indexed: KEY[0], rec_no: KEY[1]]))
RecordQueryPlan plan = planner.plan(query);
if (shouldDeferFetch || planner instanceof CascadesPlanner) {
final BindingMatcher<? extends RecordQueryPlan> planMatcher = fetchFromPartialRecordPlan(unionPlan(coveringIndexPlan().where(indexPlanOf(indexPlan().where(indexName("MySimpleRecord$num_value_3_indexed")).and(scanComparisons(range("([null],[2])"))))), coveringIndexPlan().where(indexPlanOf(indexPlan().where(indexName("MySimpleRecord$num_value_3_indexed")).and(scanComparisons(range("([3],>")))))).where(comparisonKey(concat(field("num_value_3_indexed"), primaryKey("MySimpleRecord")))));
assertMatchesExactly(plan, planMatcher);
assertEquals(-627934247, plan.planHash(PlanHashable.PlanHashKind.LEGACY));
assertEquals(502710007, plan.planHash(PlanHashable.PlanHashKind.FOR_CONTINUATION));
assertEquals(1718649364, plan.planHash(PlanHashable.PlanHashKind.STRUCTURAL_WITHOUT_LITERALS));
} else {
final BindingMatcher<? extends RecordQueryPlan> planMatcher = unionPlan(indexPlan().where(indexName("MySimpleRecord$num_value_3_indexed")).and(scanComparisons(range("([null],[2])"))), indexPlan().where(indexName("MySimpleRecord$num_value_3_indexed")).and(scanComparisons(range("([3],>")))).where(comparisonKey(concat(field("num_value_3_indexed"), primaryKey("MySimpleRecord"))));
assertMatchesExactly(plan, planMatcher);
assertEquals(-1930405164, plan.planHash(PlanHashable.PlanHashKind.LEGACY));
assertEquals(-1650830816, plan.planHash(PlanHashable.PlanHashKind.FOR_CONTINUATION));
assertEquals(-434891459, plan.planHash(PlanHashable.PlanHashKind.STRUCTURAL_WITHOUT_LITERALS));
}
try (FDBRecordContext context = openContext()) {
openSimpleRecordStore(context, hook);
int i = 0;
try (RecordCursorIterator<FDBQueriedRecord<Message>> cursor = recordStore.executeQuery(plan).asIterator()) {
while (cursor.hasNext()) {
FDBQueriedRecord<Message> rec = cursor.next();
TestRecords1Proto.MySimpleRecord.Builder myrec = TestRecords1Proto.MySimpleRecord.newBuilder();
myrec.mergeFrom(Objects.requireNonNull(rec).getRecord());
assertTrue(myrec.getNumValue3Indexed() < 2 || myrec.getNumValue3Indexed() > 3);
i++;
}
}
assertEquals(40 + 20, i);
assertDiscardedNone(context);
}
}
use of com.apple.test.BooleanSource in project fdb-record-layer by FoundationDB.
the class FDBOrQueryToUnionTest method testUnorderableOrQueryWithAnd.
/**
* Verify that a complex query with an OR of an AND produces a union plan if the appropriate indexes are defined.
* Unlike {@link #testOrQuery6()}, the legs of the union are not compatibly ordered, so this will revert to using
* an unordered union.
*/
@DualPlannerTest
@ParameterizedTest
@BooleanSource
void testUnorderableOrQueryWithAnd(boolean removesDuplicates) throws Exception {
RecordMetaDataHook hook = metaDataBuilder -> {
complexQuerySetupHook().apply(metaDataBuilder);
metaDataBuilder.addIndex("MySimpleRecord", new Index("multi_index_2", "str_value_indexed", "num_value_3_indexed"));
};
complexQuerySetup(hook);
setDeferFetchAfterUnionAndIntersection(true);
RecordQuery query = RecordQuery.newBuilder().setRecordType("MySimpleRecord").setFilter(Query.and(Query.field("str_value_indexed").equalsValue("even"), Query.or(Query.field("num_value_2").lessThanOrEquals(1), Query.field("num_value_3_indexed").greaterThanOrEquals(3)))).setRemoveDuplicates(removesDuplicates).build();
// Unordered(Index(multi_index ([even, null],[even, 1]]) ∪ Index(multi_index_2 [[even, 3],[even]]))
RecordQueryPlan plan = planner.plan(query);
BindingMatcher<? extends RecordQueryPlan> planMatcher = unorderedUnionPlan(coveringIndexPlan().where(indexPlanOf(indexPlan().where(indexName("multi_index")).and(scanComparisons(range("([even, null],[even, 1]]"))))), coveringIndexPlan().where(indexPlanOf(indexPlan().where(indexName("multi_index_2")).and(scanComparisons(range("[[even, 3],[even]]"))))));
if (removesDuplicates) {
planMatcher = fetchFromPartialRecordPlan(unorderedPrimaryKeyDistinctPlan(planMatcher));
} else {
planMatcher = fetchFromPartialRecordPlan(planMatcher);
}
assertMatchesExactly(plan, planMatcher);
assertEquals(removesDuplicates ? -1216499257 : -1216499264, plan.planHash(PlanHashable.PlanHashKind.LEGACY));
assertEquals(removesDuplicates ? 610131412 : 1405311066, plan.planHash(PlanHashable.PlanHashKind.FOR_CONTINUATION));
assertEquals(removesDuplicates ? 1591758672 : -1908028970, plan.planHash(PlanHashable.PlanHashKind.STRUCTURAL_WITHOUT_LITERALS));
try (FDBRecordContext context = openContext()) {
openSimpleRecordStore(context, hook);
int i = 0;
try (RecordCursorIterator<FDBQueriedRecord<Message>> cursor = recordStore.executeQuery(plan).asIterator()) {
while (cursor.hasNext()) {
FDBQueriedRecord<Message> rec = cursor.next();
TestRecords1Proto.MySimpleRecord.Builder myrec = TestRecords1Proto.MySimpleRecord.newBuilder();
myrec.mergeFrom(Objects.requireNonNull(rec).getRecord());
assertTrue(myrec.getStrValueIndexed().equals("even") && (myrec.getNumValue2() <= 1 || myrec.getNumValue3Indexed() >= 3));
i++;
}
}
if (removesDuplicates) {
assertEquals(40, i);
assertDiscardedAtMost(13, context);
assertLoadRecord(53, context);
} else {
assertEquals(53, i);
assertDiscardedNone(context);
}
}
}
use of com.apple.test.BooleanSource in project fdb-record-layer by FoundationDB.
the class FDBOrQueryToUnionTest method testComplexQuery6Continuations.
@DualPlannerTest
@ParameterizedTest
@BooleanSource
void testComplexQuery6Continuations(boolean shouldDeferFetch) throws Exception {
RecordMetaDataHook hook = complexQuerySetupHook();
complexQuerySetup(hook);
RecordQuery query = RecordQuery.newBuilder().setRecordType("MySimpleRecord").setFilter(Query.or(Query.field("str_value_indexed").equalsValue("odd"), Query.field("num_value_3_indexed").equalsValue(0))).setRemoveDuplicates(true).build();
setDeferFetchAfterUnionAndIntersection(shouldDeferFetch);
RecordQueryPlan plan = planner.plan(query);
try (FDBRecordContext context = openContext()) {
openSimpleRecordStore(context, hook);
for (int limit = 1; limit <= 5; limit++) {
clearStoreCounter(context);
Set<Long> seen = new HashSet<>();
int i = 0;
byte[] continuation = null;
do {
try (RecordCursorIterator<FDBQueriedRecord<Message>> cursor = recordStore.executeQuery(plan, continuation, ExecuteProperties.newBuilder().setReturnedRowLimit(limit).build()).asIterator()) {
while (cursor.hasNext()) {
FDBQueriedRecord<Message> rec = cursor.next();
TestRecords1Proto.MySimpleRecord.Builder myrec = TestRecords1Proto.MySimpleRecord.newBuilder();
myrec.mergeFrom(Objects.requireNonNull(rec).getRecord());
assertTrue(myrec.getStrValueIndexed().equals("odd") || myrec.getNumValue3Indexed() == 0, "condition on record not met");
assertFalse(seen.contains(myrec.getRecNo()), "Already saw a record!");
seen.add(myrec.getRecNo());
i++;
}
continuation = cursor.getContinuation();
}
} while (continuation != null);
assertEquals(60, i);
assertDiscardedExactly(10, context);
if (shouldDeferFetch) {
assertLoadRecord(60, context);
}
}
}
}
Aggregations