Author: chetanm
Date: Thu Jul 6 10:15:08 2017
New Revision: 1801011
URL: http://svn.apache.org/viewvc?rev=1801011&view=rev
Log:
OAK-6333 - IndexPlanner should use actual entryCount instead of limiting it to
1000
Default behaviour changed to use actual numDocs.
Modified:
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexPlanner.java
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexPlannerTest.java
Modified:
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexPlanner.java
URL:
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexPlanner.java?rev=1801011&r1=1801010&r2=1801011&view=diff
==============================================================================
---
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexPlanner.java
(original)
+++
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexPlanner.java
Thu Jul 6 10:15:08 2017
@@ -58,6 +58,7 @@ import static org.apache.jackrabbit.oak.
import static org.apache.jackrabbit.oak.spi.query.QueryIndex.OrderEntry;
class IndexPlanner {
+ private static final String FLAG_ENTRY_COUNT =
"oak.lucene.useActualEntryCount";
private static final Logger log =
LoggerFactory.getLogger(IndexPlanner.class);
private final IndexDefinition definition;
private final Filter filter;
@@ -65,6 +66,15 @@ class IndexPlanner {
private final List<OrderEntry> sortOrder;
private IndexNode indexNode;
private PlanResult result;
+ private static boolean useActualEntryCount = false;
+
+ static {
+ useActualEntryCount =
Boolean.parseBoolean(System.getProperty(FLAG_ENTRY_COUNT, "true"));
+ if (!useActualEntryCount) {
+ log.info("System property {} found to be false. IndexPlanner would
use a default entryCount of 1000 instead" +
+ " of using the actual entry count", FLAG_ENTRY_COUNT);
+ }
+ }
public IndexPlanner(IndexNode indexNode,
String indexPath,
@@ -106,6 +116,11 @@ class IndexPlanner {
'}';
}
+ //For tests
+ static void setUseActualEntryCount(boolean useActualEntryCount) {
+ IndexPlanner.useActualEntryCount = useActualEntryCount;
+ }
+
private IndexPlan.Builder getPlanBuilder() {
log.trace("Evaluating plan with index definition {}", definition);
FullTextExpression ft = filter.getFullTextConstraint();
@@ -474,14 +489,23 @@ class IndexPlanner {
}
private long estimatedEntryCount() {
+ int numOfDocs = getReader().numDocs();
+ if (useActualEntryCount) {
+ return definition.isEntryCountDefined() ?
definition.getEntryCount() : numOfDocs;
+ } else {
+ return estimatedEntryCount_Compat(numOfDocs);
+ }
+ }
+
+ private long estimatedEntryCount_Compat(int numOfDocs) {
//Other index only compete in case of property indexes. For fulltext
//index return true count so as to allow multiple property indexes
//to be compared fairly
FullTextExpression ft = filter.getFullTextConstraint();
if (ft != null && definition.isFullTextEnabled()){
- return definition.getFulltextEntryCount(getReader().numDocs());
+ return definition.getFulltextEntryCount(numOfDocs);
}
- return Math.min(definition.getEntryCount(), getReader().numDocs());
+ return Math.min(definition.getEntryCount(), numOfDocs);
}
private String getPathPrefix() {
Modified:
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexPlannerTest.java
URL:
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexPlannerTest.java?rev=1801011&r1=1801010&r2=1801011&view=diff
==============================================================================
---
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexPlannerTest.java
(original)
+++
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexPlannerTest.java
Thu Jul 6 10:15:08 2017
@@ -81,6 +81,7 @@ import org.apache.lucene.index.IndexWrit
import org.apache.lucene.index.IndexWriterConfig;
import org.apache.lucene.store.Directory;
import org.apache.lucene.store.RAMDirectory;
+import org.junit.After;
import org.junit.Test;
import com.google.common.collect.ImmutableList;
@@ -90,6 +91,11 @@ public class IndexPlannerTest {
private NodeBuilder builder = root.builder();
+ @After
+ public void cleanup(){
+ IndexPlanner.setUseActualEntryCount(true);
+ }
+
@Test
public void planForSortField() throws Exception{
NodeBuilder defn = newLucenePropertyIndexDefinition(builder, "test",
of("foo"), "async");
@@ -310,6 +316,7 @@ public class IndexPlannerTest {
NodeBuilder defn = newLucenePropertyIndexDefinition(builder, "test",
of("foo"), "async");
long numofDocs = IndexDefinition.DEFAULT_ENTRY_COUNT + 1000;
+ IndexPlanner.setUseActualEntryCount(false);
IndexDefinition idxDefn = new IndexDefinition(root,
defn.getNodeState(), "/foo");
IndexNode node = createIndexNode(idxDefn, numofDocs);
FilterImpl filter = createFilter("nt:base");
@@ -344,6 +351,38 @@ public class IndexPlannerTest {
}
@Test
+ public void propertyIndexCostActualByDefault() throws Exception{
+ NodeBuilder defn = newLucenePropertyIndexDefinition(builder, "test",
of("foo"), "async");
+ long entryCount = IndexDefinition.DEFAULT_ENTRY_COUNT - 100;
+ defn.setProperty(IndexConstants.ENTRY_COUNT_PROPERTY_NAME, entryCount);
+
+ long numofDocs = IndexDefinition.DEFAULT_ENTRY_COUNT + 100;
+
+ IndexNode node = createIndexNode(new IndexDefinition(root,
defn.getNodeState(), "/foo"), numofDocs);
+ FilterImpl filter = createFilter("nt:base");
+ filter.restrictProperty("foo", Operator.EQUAL,
PropertyValues.newString("bar"));
+ IndexPlanner planner = new IndexPlanner(node, "/foo", filter,
Collections.<OrderEntry>emptyList());
+ QueryIndex.IndexPlan plan = planner.getPlan();
+
+ assertEquals(entryCount, plan.getEstimatedEntryCount());
+ }
+
+ @Test
+ public void propertyIndexCostActualOverriddenByEntryCount() throws
Exception{
+ NodeBuilder defn = newLucenePropertyIndexDefinition(builder, "test",
of("foo"), "async");
+
+ long numofDocs = IndexDefinition.DEFAULT_ENTRY_COUNT + 100;
+
+ IndexNode node = createIndexNode(new IndexDefinition(root,
defn.getNodeState(), "/foo"), numofDocs);
+ FilterImpl filter = createFilter("nt:base");
+ filter.restrictProperty("foo", Operator.EQUAL,
PropertyValues.newString("bar"));
+ IndexPlanner planner = new IndexPlanner(node, "/foo", filter,
Collections.<OrderEntry>emptyList());
+ QueryIndex.IndexPlan plan = planner.getPlan();
+
+ assertEquals(numofDocs, plan.getEstimatedEntryCount());
+ }
+
+ @Test
public void fulltextIndexCost() throws Exception{
NodeBuilder index = builder.child(INDEX_DEFINITIONS_NAME);
NodeBuilder defn = newLuceneIndexDefinition(index, "lucene",