Author: chetanm
Date: Fri May 12 09:14:27 2017
New Revision: 1794947
URL: http://svn.apache.org/viewvc?rev=1794947&view=rev
Log:
OAK-6192 - Lucene IndexInfoProvider implementation
Compute the diff between stored index definition and current index
definition. The diff needs to ignore system generated properties like
reindexCount, reindex etc
Modified:
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexInfoProvider.java
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LucenePropertyIndexTest.java
Modified:
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexInfoProvider.java
URL:
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexInfoProvider.java?rev=1794947&r1=1794946&r2=1794947&view=diff
==============================================================================
---
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexInfoProvider.java
(original)
+++
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexInfoProvider.java
Fri May 12 09:14:27 2017
@@ -23,10 +23,12 @@ import java.io.File;
import java.io.IOException;
import java.util.Set;
+import com.google.common.collect.ImmutableSet;
import com.google.common.collect.Iterables;
import com.google.common.collect.Sets;
import org.apache.jackrabbit.oak.api.PropertyState;
import org.apache.jackrabbit.oak.api.Type;
+import org.apache.jackrabbit.oak.json.JsopDiff;
import org.apache.jackrabbit.oak.plugins.index.AsyncIndexInfo;
import org.apache.jackrabbit.oak.plugins.index.AsyncIndexInfoService;
import org.apache.jackrabbit.oak.plugins.index.IndexConstants;
@@ -35,6 +37,7 @@ import org.apache.jackrabbit.oak.plugins
import org.apache.jackrabbit.oak.plugins.index.lucene.directory.DirectoryUtils;
import
org.apache.jackrabbit.oak.plugins.index.lucene.directory.IndexConsistencyChecker;
import
org.apache.jackrabbit.oak.plugins.index.lucene.writer.MultiplexersLucene;
+import org.apache.jackrabbit.oak.spi.state.EqualsDiff;
import org.apache.jackrabbit.oak.spi.state.NodeState;
import org.apache.jackrabbit.oak.spi.state.NodeStateUtils;
import org.apache.jackrabbit.oak.spi.state.NodeStore;
@@ -42,11 +45,15 @@ import org.apache.jackrabbit.oak.spi.sta
import org.apache.jackrabbit.util.ISO8601;
import org.apache.lucene.index.DirectoryReader;
import org.apache.lucene.store.Directory;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
import static com.google.common.base.Preconditions.checkArgument;
import static com.google.common.base.Preconditions.checkNotNull;
+import static
org.apache.jackrabbit.oak.plugins.index.lucene.IndexDefinition.INDEX_DEFINITION_NODE;
public class LuceneIndexInfoProvider implements IndexInfoProvider {
+ private final Logger log = LoggerFactory.getLogger(getClass());
private final NodeStore nodeStore;
@@ -87,6 +94,7 @@ public class LuceneIndexInfoProvider imp
LuceneIndexInfo info = new LuceneIndexInfo(indexPath);
computeSize(idxState, info);
+ computeIndexDefinitionChange(idxState, info);
computeLastUpdatedTime(idxState, info);
computeAsyncIndexInfo(idxState, indexPath, info);
return info;
@@ -100,8 +108,10 @@ public class LuceneIndexInfoProvider imp
private void computeAsyncIndexInfo(NodeState idxState, String indexPath,
LuceneIndexInfo info) {
String asyncName = getAsyncName(idxState, indexPath);
- checkNotNull(asyncName, "No 'async' value for index definition " +
- "at [%s]. Definition %s", indexPath, idxState);
+ if (asyncName == null) {
+ log.warn("No 'async' value for index definition at [{}].
Definition {}", indexPath, idxState);
+ return;
+ }
AsyncIndexInfo asyncInfo = asyncInfoService.getInfo(asyncName);
checkNotNull(asyncInfo, "No async info found for name [%s] " +
@@ -134,6 +144,17 @@ public class LuceneIndexInfoProvider imp
}
}
+ private static void computeIndexDefinitionChange(NodeState idxState,
LuceneIndexInfo info) {
+ NodeState storedDefn = idxState.getChildNode(INDEX_DEFINITION_NODE);
+ if (storedDefn.exists()) {
+ NodeState currentDefn =
NodeStateCloner.cloneVisibleState(idxState);
+ if (!FilteringEqualsDiff.equals(storedDefn, currentDefn)){
+ info.indexDefinitionChanged = true;
+ info.indexDiff = JsopDiff.diffToJsop(storedDefn, currentDefn);
+ }
+ }
+ }
+
private static class LuceneIndexInfo implements IndexInfo {
String indexPath;
String asyncName;
@@ -141,6 +162,8 @@ public class LuceneIndexInfoProvider imp
long size;
long indexedUptoTime;
long lastUpdatedTime;
+ boolean indexDefinitionChanged;
+ String indexDiff;
public LuceneIndexInfo(String indexPath) {
this.indexPath = indexPath;
@@ -183,12 +206,51 @@ public class LuceneIndexInfoProvider imp
@Override
public boolean hasIndexDefinitionChangedWithoutReindexing() {
- return false; //TODO To be computed
+ return indexDefinitionChanged;
}
@Override
public String getIndexDefinitionDiff() {
- return null;
+ return indexDiff;
+ }
+ }
+
+ static class FilteringEqualsDiff extends EqualsDiff {
+ private static final Set<String> IGNORED_PROP_NAMES = ImmutableSet.of(
+ IndexConstants.REINDEX_COUNT,
+ IndexConstants.REINDEX_PROPERTY_NAME
+ );
+ public static boolean equals(NodeState before, NodeState after) {
+ return before.exists() == after.exists()
+ && after.compareAgainstBaseState(before, new
FilteringEqualsDiff());
+ }
+
+ @Override
+ public boolean propertyChanged(PropertyState before, PropertyState
after) {
+ if (ignoredProp(before.getName())){
+ return true;
+ }
+ return false;
+ }
+
+ @Override
+ public boolean propertyAdded(PropertyState after) {
+ if (ignoredProp(after.getName())){
+ return true;
+ }
+ return super.propertyAdded(after);
+ }
+
+ @Override
+ public boolean propertyDeleted(PropertyState before) {
+ if (ignoredProp(before.getName())){
+ return true;
+ }
+ return super.propertyDeleted(before);
+ }
+
+ private boolean ignoredProp(String name) {
+ return IGNORED_PROP_NAMES.contains(name) ||
NodeStateUtils.isHidden(name);
}
}
}
Modified:
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LucenePropertyIndexTest.java
URL:
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LucenePropertyIndexTest.java?rev=1794947&r1=1794946&r2=1794947&view=diff
==============================================================================
---
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LucenePropertyIndexTest.java
(original)
+++
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LucenePropertyIndexTest.java
Fri May 12 09:14:27 2017
@@ -67,6 +67,7 @@ import static org.junit.Assert.assertEqu
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotEquals;
import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertThat;
import static org.junit.Assert.assertTrue;
@@ -105,7 +106,10 @@ import org.apache.jackrabbit.oak.api.Res
import org.apache.jackrabbit.oak.api.Tree;
import org.apache.jackrabbit.oak.api.Type;
import org.apache.jackrabbit.oak.commons.concurrent.ExecutorCloser;
+import org.apache.jackrabbit.oak.plugins.index.AsyncIndexInfoService;
+import org.apache.jackrabbit.oak.plugins.index.AsyncIndexInfoServiceImpl;
import org.apache.jackrabbit.oak.plugins.index.IndexConstants;
+import org.apache.jackrabbit.oak.plugins.index.IndexInfo;
import org.apache.jackrabbit.oak.plugins.index.fulltext.ExtractedText;
import
org.apache.jackrabbit.oak.plugins.index.fulltext.ExtractedText.ExtractionResult;
import
org.apache.jackrabbit.oak.plugins.index.fulltext.PreExtractedTextProvider;
@@ -2541,6 +2545,32 @@ public class LucenePropertyIndexTest ext
assertFalse(NodeStateUtils.getNode(nodeStore.getRoot(),
clonedDefnPath).exists());
}
+ @Test
+ public void storedIndexDefinitionDiff() throws Exception{
+ IndexDefinitionBuilder idxb = new IndexDefinitionBuilder().noAsync();
+ idxb.indexRule("nt:base").property("foo").propertyIndex();
+ Tree idx = root.getTree("/").getChild("oak:index").addChild("test1");
+ idxb.build(idx);
+ root.commit();
+
+ AsyncIndexInfoService asyncService = new
AsyncIndexInfoServiceImpl(nodeStore);
+ LuceneIndexInfoProvider indexInfoProvider = new
LuceneIndexInfoProvider(nodeStore, asyncService, temporaryFolder.newFolder());
+
+ IndexInfo info = indexInfoProvider.getInfo("/oak:index/test1");
+ assertNotNull(info);
+
+ assertFalse(info.hasIndexDefinitionChangedWithoutReindexing());
+ assertNull(info.getIndexDefinitionDiff());
+
+ Tree idxTree = root.getTree("/oak:index/test1");
+ idxTree.setProperty("foo", "bar");
+ root.commit();
+
+ info = indexInfoProvider.getInfo("/oak:index/test1");
+ assertTrue(info.hasIndexDefinitionChangedWithoutReindexing());
+ assertNotNull(info.getIndexDefinitionDiff());
+ }
+
private void assertPlanAndQuery(String query, String planExpectation,
List<String> paths){
assertThat(explain(query), containsString(planExpectation));
assertQuery(query, paths);