You are viewing a plain text version of this content. The canonical link for it is here.
Posted to oak-commits@jackrabbit.apache.org by ch...@apache.org on 2014/11/26 09:06:53 UTC
svn commit: r1641771 [2/2] - in /jackrabbit/oak/trunk/oak-lucene/src:
main/java/org/apache/jackrabbit/oak/plugins/index/lucene/
main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/
test/java/org/apache/jackrabbit/oak/plugins/index/lucene/
Added: jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/AggregateTest.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/AggregateTest.java?rev=1641771&view=auto
==============================================================================
--- jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/AggregateTest.java (added)
+++ jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/AggregateTest.java Wed Nov 26 08:06:52 2014
@@ -0,0 +1,416 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.jackrabbit.oak.plugins.index.lucene;
+
+import java.util.Collection;
+import java.util.List;
+import java.util.Map;
+
+import com.google.common.collect.ArrayListMultimap;
+import com.google.common.collect.ListMultimap;
+import com.google.common.collect.Lists;
+import org.apache.jackrabbit.oak.api.CommitFailedException;
+import org.apache.jackrabbit.oak.commons.PathUtils;
+import org.apache.jackrabbit.oak.plugins.index.lucene.Aggregate.NodeInclude;
+import org.apache.jackrabbit.oak.plugins.index.lucene.Aggregate.NodeIncludeResult;
+import org.apache.jackrabbit.oak.plugins.index.lucene.Aggregate.PropertyIncludeResult;
+import org.apache.jackrabbit.oak.spi.state.NodeBuilder;
+import org.apache.jackrabbit.oak.spi.state.NodeState;
+import org.junit.Test;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static com.google.common.collect.ImmutableList.of;
+import static com.google.common.collect.Iterables.toArray;
+import static com.google.common.collect.Maps.newHashMap;
+import static org.apache.jackrabbit.JcrConstants.JCR_PRIMARYTYPE;
+import static org.apache.jackrabbit.oak.plugins.index.lucene.LuceneIndexConstants.INDEX_RULES;
+import static org.apache.jackrabbit.oak.plugins.memory.EmptyNodeState.EMPTY_NODE;
+import static org.apache.jackrabbit.oak.plugins.nodetype.write.InitialContent.INITIAL_CONTENT;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertThat;
+import static org.junit.Assert.assertTrue;
+import static org.junit.matchers.JUnitMatchers.hasItems;
+
+public class AggregateTest {
+
+ private final TestCollector col = new TestCollector();
+ private final SimpleMapper mapper = new SimpleMapper();
+ private final NodeState root = INITIAL_CONTENT;
+ private NodeBuilder builder = root.builder();
+
+ //~---------------------------------< Node Includes >
+
+ @Test
+ public void oneLevelAll() throws Exception{
+ Aggregate ag = new Aggregate("nt:base", of(ni("*")));
+ NodeBuilder nb = newNode("nt:base");
+ nb.child("a").child("c");
+ nb.child("b");
+
+ ag.collectAggregates(nb.getNodeState(), col);
+ assertEquals(2, col.getNodePaths().size());
+ assertThat(col.getNodePaths(), hasItems("a", "b"));
+ }
+
+ @Test
+ public void oneLevelNamed() throws Exception{
+ Aggregate ag = new Aggregate("nt:base", of(ni("a")));
+ NodeBuilder nb = newNode("nt:base");
+ nb.child("a");
+ nb.child("b");
+
+ ag.collectAggregates(nb.getNodeState(), col);
+ assertEquals(1, col.getNodePaths().size());
+ assertThat(col.getNodePaths(), hasItems("a"));
+ }
+
+ @Test
+ public void oneLevelTyped() throws Exception{
+ Aggregate ag = new Aggregate("nt:base", of(ni("nt:resource","*", false)));
+ NodeBuilder nb = newNode("nt:base");
+ nb.child("a").setProperty(JCR_PRIMARYTYPE,"nt:resource");
+ nb.child("b");
+
+ ag.collectAggregates(nb.getNodeState(), col);
+ assertEquals(1, col.getNodePaths().size());
+ assertThat(col.getNodePaths(), hasItems("a"));
+ }
+
+ @Test
+ public void multiLevelAll() throws Exception{
+ Aggregate ag = new Aggregate("nt:base", of(ni("*"), ni("*/*")));
+ NodeBuilder nb = newNode("nt:base");
+ nb.child("a").child("c");
+ nb.child("b");
+ nb.child("d").child("e").child("f");
+
+ ag.collectAggregates(nb.getNodeState(), col);
+ assertEquals(5, col.getNodePaths().size());
+ assertThat(col.getNodePaths(), hasItems("a", "b", "d", "a/c", "d/e"));
+ }
+
+ @Test
+ public void multiLevelNamed() throws Exception{
+ Aggregate ag = new Aggregate("nt:base", of(ni("a"), ni("d/e")));
+ NodeBuilder nb = newNode("nt:base");
+ nb.child("a").child("c");
+ nb.child("b");
+ nb.child("d").child("e").child("f");
+
+ ag.collectAggregates(nb.getNodeState(), col);
+ assertEquals(2, col.getNodePaths().size());
+ assertThat(col.getNodePaths(), hasItems("a", "d/e"));
+ }
+
+ @Test
+ public void multiLevelTyped() throws Exception{
+ Aggregate ag = new Aggregate("nt:base", of(ni("a"),
+ ni("nt:resource", "d/*/*", false)));
+ NodeBuilder nb = newNode("nt:base");
+ nb.child("a").child("c");
+ nb.child("b");
+ nb.child("d").child("e").child("f").setProperty(JCR_PRIMARYTYPE,"nt:resource");
+ nb.child("d").child("e").child("f2");
+ nb.child("d").child("e2").child("f3").setProperty(JCR_PRIMARYTYPE, "nt:resource");
+
+ ag.collectAggregates(nb.getNodeState(), col);
+ assertEquals(3, col.getNodePaths().size());
+ assertThat(col.getNodePaths(), hasItems("a", "d/e/f", "d/e2/f3"));
+ }
+
+ @Test
+ public void multiLevelNamedSubAll() throws Exception{
+ Aggregate ag = new Aggregate("nt:base", of(ni("a"), ni("d/*/*")));
+ NodeBuilder nb = newNode("nt:base");
+ nb.child("a").child("c");
+ nb.child("b");
+ nb.child("d").child("e").child("f");
+ nb.child("d").child("e").child("f2");
+ nb.child("d").child("e2").child("f3");
+
+ ag.collectAggregates(nb.getNodeState(), col);
+ assertEquals(4, col.getNodePaths().size());
+ assertThat(col.getNodePaths(), hasItems("a", "d/e/f", "d/e/f2", "d/e2/f3"));
+ }
+
+ //~---------------------------------< Node include recursive >
+
+ @Test
+ public void multiAggregateMapping() throws Exception{
+ Aggregate ag = new Aggregate("nt:base", of(ni("*")));
+
+ Aggregate agFile = new Aggregate("nt:file", of(ni("*"), ni("*/*")));
+ mapper.add("nt:file", agFile);
+
+ NodeBuilder nb = newNode("nt:base");
+ nb.child("a").child("c");
+ nb.child("b").setProperty(JCR_PRIMARYTYPE, "nt:file");
+ nb.child("b").child("b1").child("b2");
+ nb.child("c");
+
+ ag.collectAggregates(nb.getNodeState(), col);
+ assertEquals(5, col.getNodePaths().size());
+ assertThat(col.getNodePaths(), hasItems("a", "b", "c", "b/b1", "b/b1/b2"));
+ }
+
+ @Test
+ public void recursionEnabled() throws Exception{
+ Aggregate agFile = new Aggregate("nt:file", of(ni("*")), 5);
+ mapper.add("nt:file", agFile);
+
+ NodeBuilder nb = newNode("nt:file");
+ nb.child("a").child("c");
+ nb.child("b").setProperty(JCR_PRIMARYTYPE, "nt:file");
+ nb.child("b").child("b1").child("b2");
+ nb.child("c");
+
+ agFile.collectAggregates(nb.getNodeState(), col);
+ assertEquals(4, col.getNodePaths().size());
+ assertThat(col.getNodePaths(), hasItems("a", "b", "c", "b/b1"));
+ }
+
+ @Test
+ public void recursionEnabledWithLimitCheck() throws Exception{
+ int limit = 5;
+ Aggregate agFile = new Aggregate("nt:file", of(ni("*")), limit);
+ mapper.add("nt:file", agFile);
+
+ List<String> expectedPaths = Lists.newArrayList();
+ NodeBuilder nb = newNode("nt:file");
+ nb.child("a").child("c");
+
+ String path = "";
+ NodeBuilder fb = nb;
+ for (int i = 0; i < limit + 2; i++){
+ String name = "f "+ i;
+ path = PathUtils.concat(path, name);
+ fb = fb.child(name);
+ fb.setProperty(JCR_PRIMARYTYPE, "nt:file");
+
+ if (i < limit) {
+ expectedPaths.add(path);
+ }
+ }
+ expectedPaths.add("a");
+
+ agFile.collectAggregates(nb.getNodeState(), col);
+ assertEquals(expectedPaths.size(), col.getNodePaths().size());
+ assertThat(col.getNodePaths(), hasItems(toArray(expectedPaths, String.class)));
+ }
+
+ @Test
+ public void includeMatches() throws Exception{
+ Aggregate ag = new Aggregate("nt:base", of(ni(null, "*", true), ni(null, "*/*", true)));
+ assertTrue(ag.hasRelativeNodeInclude("foo"));
+ assertTrue(ag.hasRelativeNodeInclude("foo/bar"));
+ assertFalse(ag.hasRelativeNodeInclude("foo/bar/baz"));
+
+
+ Aggregate ag2 = new Aggregate("nt:base", of(ni(null, "foo", true), ni(null, "foo/*", true)));
+ assertTrue(ag2.hasRelativeNodeInclude("foo"));
+ assertFalse(ag2.hasRelativeNodeInclude("bar"));
+ assertTrue(ag2.hasRelativeNodeInclude("foo/bar"));
+ assertFalse(ag2.hasRelativeNodeInclude("foo/bar/baz"));
+ }
+
+ @Test
+ public void testReaggregate() throws Exception{
+ //Enable relative include for all child nodes of nt:folder
+ //So indexing would create fulltext field for each relative nodes
+ Aggregate agFolder = new Aggregate("nt:folder", of(ni("nt:file", "*", true)));
+
+ Aggregate agFile = new Aggregate("nt:file", of(ni(null, "jcr:content", true)));
+ mapper.add("nt:file", agFile);
+ mapper.add("nt:folder", agFolder);
+
+ NodeBuilder nb = newNode("nt:folder");
+ nb.child("a").child("c");
+ createFile(nb, "b", "hello world");
+ createFile(nb, "c", "hello world");
+
+ agFolder.collectAggregates(nb.getNodeState(), col);
+ assertEquals(4, col.getNodePaths().size());
+ assertThat(col.getNodePaths(), hasItems("b", "c", "b/jcr:content", "c/jcr:content"));
+
+ assertEquals(2, col.nodeResults.get("b/jcr:content").size());
+
+ //Check that a result is provided for relative node 'b'. Actual node provided
+ //is b/jcr:content
+ assertEquals(1, col.getRelativeNodeResults("b/jcr:content", "b").size());
+ }
+
+ private static void createFile(NodeBuilder nb, String fileName, String content){
+ nb.child(fileName).setProperty(JCR_PRIMARYTYPE, "nt:file")
+ .child("jcr:content").setProperty("jcr:data", content.getBytes());
+ }
+
+ //~---------------------------------< Prop Includes >
+
+ @Test
+ public void propOneLevelNamed() throws Exception{
+ NodeBuilder rules = builder.child(INDEX_RULES);
+ rules.child("nt:folder");
+ child(rules, "nt:folder/properties/p1")
+ .setProperty(LuceneIndexConstants.PROP_NAME, "a/p1");
+
+ IndexDefinition defn = new IndexDefinition(root, builder.getNodeState());
+ Aggregate ag = defn.getApplicableIndexingRule("nt:folder").getAggregate();
+
+ NodeBuilder nb = newNode("nt:folder");
+ nb.child("a").setProperty("p1", "foo");
+ nb.child("a").setProperty("p2", "foo");
+ nb.child("b").setProperty("p2", "foo");
+
+ ag.collectAggregates(nb.getNodeState(), col);
+ assertEquals(1, col.getPropPaths().size());
+ assertThat(col.getPropPaths(), hasItems("a/p1"));
+ }
+
+ @Test
+ public void propOneLevelRegex() throws Exception{
+ NodeBuilder rules = builder.child(INDEX_RULES);
+ rules.child("nt:folder");
+ child(rules, "nt:folder/properties/p1")
+ .setProperty(LuceneIndexConstants.PROP_NAME, "a/foo.*")
+ .setProperty(LuceneIndexConstants.PROP_IS_REGEX, true);
+
+ IndexDefinition defn = new IndexDefinition(root, builder.getNodeState());
+ Aggregate ag = defn.getApplicableIndexingRule("nt:folder").getAggregate();
+
+ NodeBuilder nb = newNode("nt:folder");
+ nb.child("a").setProperty("foo1", "foo");
+ nb.child("a").setProperty("foo2", "foo");
+ nb.child("a").setProperty("bar1", "foo");
+ nb.child("b").setProperty("p2", "foo");
+
+ ag.collectAggregates(nb.getNodeState(), col);
+ assertEquals(2, col.getPropPaths().size());
+ assertThat(col.getPropPaths(), hasItems("a/foo1", "a/foo2"));
+ }
+
+ //~---------------------------------< IndexingConfig >
+
+ @Test
+ public void simpleAggregateConfig() throws Exception{
+ NodeBuilder aggregates = builder.child(LuceneIndexConstants.AGGREGATES);
+ NodeBuilder aggFolder = aggregates.child("nt:folder");
+ aggFolder.child("i1").setProperty(LuceneIndexConstants.AGG_PATH, "*");
+
+ IndexDefinition defn = new IndexDefinition(root, builder.getNodeState());
+ Aggregate agg = defn.getAggregate("nt:folder");
+ assertNotNull(agg);
+ assertEquals(1, agg.getIncludes().size());
+ }
+
+ @Test
+ public void aggregateConfig2() throws Exception{
+ NodeBuilder aggregates = builder.child(LuceneIndexConstants.AGGREGATES);
+ NodeBuilder aggFolder = aggregates.child("nt:folder");
+ aggFolder.setProperty(LuceneIndexConstants.AGG_RECURSIVE_LIMIT, 42);
+ aggFolder.child("i1").setProperty(LuceneIndexConstants.AGG_PATH, "*");
+ aggFolder.child("i1").setProperty(LuceneIndexConstants.AGG_PRIMARY_TYPE, "nt:file");
+ aggFolder.child("i1").setProperty(LuceneIndexConstants.AGG_RELATIVE_NODE, true);
+
+ IndexDefinition defn = new IndexDefinition(root, builder.getNodeState());
+ Aggregate agg = defn.getAggregate("nt:folder");
+ assertNotNull(agg);
+ assertEquals(42, agg.reAggregationLimit);
+ assertEquals(1, agg.getIncludes().size());
+ assertEquals("nt:file", ((NodeInclude)agg.getIncludes().get(0)).primaryType);
+ assertTrue(((NodeInclude)agg.getIncludes().get(0)).relativeNode);
+ }
+
+ private static NodeBuilder newNode(String typeName){
+ NodeBuilder builder = EMPTY_NODE.builder();
+ builder.setProperty(JCR_PRIMARYTYPE, typeName);
+ return builder;
+ }
+
+ private static NodeBuilder child(NodeBuilder nb, String path) {
+ for (String name : PathUtils.elements(checkNotNull(path))) {
+ nb = nb.child(name);
+ }
+ return nb;
+ }
+
+ private Aggregate.Include ni(String pattern){
+ return new NodeInclude(mapper, pattern);
+ }
+
+ private Aggregate.Include ni(String type, String pattern, boolean relativeNode){
+ return new NodeInclude(mapper, type, pattern, relativeNode);
+ }
+
+ private static class TestCollector implements Aggregate.ResultCollector {
+ final ListMultimap<String, NodeIncludeResult> nodeResults = ArrayListMultimap.create();
+ final Map<String, PropertyIncludeResult> propResults = newHashMap();
+ @Override
+ public void onResult(NodeIncludeResult result) throws CommitFailedException{
+ nodeResults.put(result.nodePath, result);
+ }
+
+ @Override
+ public void onResult(PropertyIncludeResult result) throws CommitFailedException {
+ propResults.put(result.propertyPath, result);
+
+ }
+
+ public Collection<String> getNodePaths(){
+ return nodeResults.keySet();
+ }
+
+ public Collection<String> getPropPaths(){
+ return propResults.keySet();
+ }
+
+ public void reset(){
+ nodeResults.clear();
+ propResults.clear();
+ }
+
+ public List<NodeIncludeResult> getRelativeNodeResults(String path, String rootIncludePath){
+ List<NodeIncludeResult> result = Lists.newArrayList();
+
+ for (NodeIncludeResult nr : nodeResults.get(path)){
+ if (rootIncludePath.equals(nr.rootIncludePath)){
+ result.add(nr);
+ }
+ }
+
+ return result;
+ }
+ }
+
+ private static class SimpleMapper implements Aggregate.AggregateMapper {
+ final Map<String, Aggregate> mapping = newHashMap();
+
+ @Override
+ public Aggregate getAggregate(String nodeTypeName) {
+ return mapping.get(nodeTypeName);
+ }
+
+ public void add(String type, Aggregate agg){
+ mapping.put(type, agg);
+ }
+ }
+
+}
Propchange: jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/AggregateTest.java
------------------------------------------------------------------------------
svn:eol-style = native
Modified: jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexDefinitionTest.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexDefinitionTest.java?rev=1641771&r1=1641770&r2=1641771&view=diff
==============================================================================
--- jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexDefinitionTest.java (original)
+++ jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexDefinitionTest.java Wed Nov 26 08:06:52 2014
@@ -22,7 +22,6 @@ package org.apache.jackrabbit.oak.plugin
import javax.jcr.PropertyType;
import com.google.common.collect.ImmutableList;
-import com.google.common.collect.Iterables;
import org.apache.jackrabbit.JcrConstants;
import org.apache.jackrabbit.oak.api.Tree;
import org.apache.jackrabbit.oak.commons.PathUtils;
@@ -141,25 +140,12 @@ public class IndexDefinitionTest {
}
@Test
- public void relativeProperty() throws Exception{
- builder.setProperty(createProperty(INCLUDE_PROPERTY_NAMES, of("foo" , "foo1/bar"), STRINGS));
- IndexDefinition idxDefn = new IndexDefinition(root, builder.getNodeState());
- IndexingRule rule = idxDefn.getApplicableIndexingRule(NT_BASE);
-
- assertEquals(1, rule.getRelativeProps().size());
- assertEquals("foo1/bar", Iterables.getFirst(rule.getRelativeProps(), null).propertyPath);
- assertTrue(idxDefn.hasRelativeProperty("bar"));
- assertFalse(idxDefn.hasRelativeProperty("foo"));
- }
-
- @Test
public void relativePropertyConfig() throws Exception{
builder.child(PROP_NODE).child("foo1").child("bar").setProperty(LuceneIndexConstants.PROP_TYPE, PropertyType.TYPENAME_DATE);
builder.child(PROP_NODE).child("foo2").child("bar2").child("baz").setProperty(LuceneIndexConstants.PROP_TYPE, PropertyType.TYPENAME_LONG);
builder.setProperty(createProperty(INCLUDE_PROPERTY_NAMES, of("foo", "foo1/bar", "foo2/bar2/baz"), STRINGS));
IndexDefinition defn = new IndexDefinition(root, builder.getNodeState());
IndexingRule rule = defn.getApplicableIndexingRule(newTree(newNode("nt:folder")));
- assertEquals(2, defn.getRelativeProps().size());
assertNotNull(rule.getConfig("foo1/bar"));
assertEquals(PropertyType.DATE, rule.getConfig("foo1/bar").getType());
assertEquals(PropertyType.LONG, rule.getConfig("foo2/bar2/baz").getType());
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=1641771&r1=1641770&r2=1641771&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 Wed Nov 26 08:06:52 2014
@@ -30,8 +30,8 @@ import org.apache.jackrabbit.oak.query.a
import org.apache.jackrabbit.oak.query.ast.SelectorImpl;
import org.apache.jackrabbit.oak.query.fulltext.FullTextParser;
import org.apache.jackrabbit.oak.query.index.FilterImpl;
-import org.apache.jackrabbit.oak.spi.commit.CommitInfo;
import org.apache.jackrabbit.oak.spi.query.PropertyValues;
+import org.apache.jackrabbit.oak.spi.query.QueryIndex;
import org.apache.jackrabbit.oak.spi.state.NodeBuilder;
import org.apache.jackrabbit.oak.spi.state.NodeState;
import org.apache.lucene.document.Document;
@@ -48,19 +48,18 @@ import static javax.jcr.PropertyType.TYP
import static org.apache.jackrabbit.JcrConstants.JCR_SYSTEM;
import static org.apache.jackrabbit.oak.api.Type.STRINGS;
import static org.apache.jackrabbit.oak.plugins.index.IndexConstants.INDEX_DEFINITIONS_NAME;
-import static org.apache.jackrabbit.oak.plugins.index.lucene.LuceneIndexConstants.INCLUDE_PROPERTY_NAMES;
import static org.apache.jackrabbit.oak.plugins.index.lucene.LuceneIndexConstants.INDEX_DATA_CHILD_NAME;
import static org.apache.jackrabbit.oak.plugins.index.lucene.LuceneIndexConstants.ORDERED_PROP_NAMES;
import static org.apache.jackrabbit.oak.plugins.index.lucene.LuceneIndexConstants.VERSION;
import static org.apache.jackrabbit.oak.plugins.index.lucene.util.LuceneIndexHelper.newLuceneIndexDefinition;
import static org.apache.jackrabbit.oak.plugins.index.lucene.util.LuceneIndexHelper.newLucenePropertyIndexDefinition;
-import static org.apache.jackrabbit.oak.plugins.memory.EmptyNodeState.EMPTY_NODE;
import static org.apache.jackrabbit.oak.plugins.memory.PropertyStates.createProperty;
import static org.apache.jackrabbit.oak.plugins.nodetype.NodeTypeConstants.JCR_NODE_TYPES;
import static org.apache.jackrabbit.oak.plugins.nodetype.write.InitialContent.INITIAL_CONTENT;
import static org.apache.jackrabbit.oak.spi.query.QueryIndex.OrderEntry;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
+import static org.junit.Assert.assertTrue;
public class IndexPlannerTest {
private NodeState root = INITIAL_CONTENT;
@@ -125,6 +124,19 @@ public class IndexPlannerTest {
IndexPlanner planner = new IndexPlanner(node, "/foo", filter, Collections.<OrderEntry>emptyList());
assertNull(planner.getPlan());
}
+ @Test
+ public void matchingProperty() throws Exception{
+ NodeBuilder defn = newLucenePropertyIndexDefinition(builder, "test", of("foo"), "async");
+ IndexNode node = createIndexNode(new IndexDefinition(root, defn.getNodeState()));
+ 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();
+ assertNotNull(plan);
+ assertNotNull(pr(plan));
+ assertTrue(pr(plan).evaluateNonFullTextConstraints());
+ }
+
@Test
public void worksWithIndexFormatV2Onwards() throws Exception{
@@ -164,4 +176,9 @@ public class IndexPlannerTest {
writer.close();
return dir;
}
+
+ private static IndexPlanner.PlanResult pr(QueryIndex.IndexPlan plan) {
+ return (IndexPlanner.PlanResult) plan.getAttribute(LucenePropertyIndex.ATTR_PLAN_RESULT);
+ }
+
}
Modified: jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexAggregationTest.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexAggregationTest.java?rev=1641771&r1=1641770&r2=1641771&view=diff
==============================================================================
--- jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexAggregationTest.java (original)
+++ jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexAggregationTest.java Wed Nov 26 08:06:52 2014
@@ -31,15 +31,17 @@ import org.apache.jackrabbit.oak.Oak;
import org.apache.jackrabbit.oak.api.ContentRepository;
import org.apache.jackrabbit.oak.api.Tree;
import org.apache.jackrabbit.oak.api.Type;
-import org.apache.jackrabbit.oak.plugins.index.aggregate.AggregateIndexProvider;
import org.apache.jackrabbit.oak.plugins.index.aggregate.NodeAggregator;
import org.apache.jackrabbit.oak.plugins.index.aggregate.SimpleNodeAggregator;
+import static org.apache.jackrabbit.oak.plugins.index.lucene.TestUtil.newNodeAggregator;
+import static org.apache.jackrabbit.oak.plugins.index.lucene.TestUtil.useV2;
import static org.apache.jackrabbit.oak.plugins.memory.BinaryPropertyState.binaryProperty;
import org.apache.jackrabbit.oak.plugins.nodetype.write.InitialContent;
import org.apache.jackrabbit.oak.query.AbstractQueryTest;
import org.apache.jackrabbit.oak.spi.commit.Observer;
+import org.apache.jackrabbit.oak.spi.query.QueryIndexProvider;
import org.apache.jackrabbit.oak.spi.security.OpenSecurityProvider;
import org.junit.Test;
@@ -51,8 +53,16 @@ public class LuceneIndexAggregationTest
protected void createTestIndexNode() throws Exception {
Tree index = root.getTree("/");
Tree indexDefn = createTestIndexNode(index, LuceneIndexConstants.TYPE_LUCENE);
- //TODO Remove compat mode once OAK-2278 resolved
- indexDefn.setProperty(LuceneIndexConstants.COMPAT_MODE, IndexFormatVersion.V1.getVersion());
+ useV2(indexDefn);
+ //Aggregates
+ newNodeAggregator(indexDefn)
+ .newRuleWithName(NT_FILE, newArrayList(JCR_CONTENT, JCR_CONTENT + "/*"))
+ .newRuleWithName(NT_FOLDER, newArrayList("myFile", "subfolder/subsubfolder/file"));
+
+ //Include all properties
+ Tree props = TestUtil.newRulePropTree(indexDefn, "nt:base");
+ TestUtil.enableForFullText(props, LuceneIndexConstants.REGEX_ALL_PROPS, true);
+
root.commit();
}
@@ -62,7 +72,7 @@ public class LuceneIndexAggregationTest
return new Oak()
.with(new InitialContent())
.with(new OpenSecurityProvider())
- .with(AggregateIndexProvider.wrap(provider.with(getNodeAggregator())))
+ .with((QueryIndexProvider)provider.with(getNodeAggregator()))
.with((Observer) provider)
.with(new LuceneIndexEditorProvider())
.createContentRepository();
Modified: jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexAggregationTest2.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexAggregationTest2.java?rev=1641771&r1=1641770&r2=1641771&view=diff
==============================================================================
--- jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexAggregationTest2.java (original)
+++ jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexAggregationTest2.java Wed Nov 26 08:06:52 2014
@@ -28,6 +28,8 @@ import static org.apache.jackrabbit.JcrC
import static org.apache.jackrabbit.oak.api.Type.NAME;
import static org.apache.jackrabbit.oak.api.Type.STRING;
import static org.apache.jackrabbit.oak.api.Type.STRINGS;
+import static org.apache.jackrabbit.oak.plugins.index.lucene.TestUtil.newNodeAggregator;
+import static org.apache.jackrabbit.oak.plugins.index.lucene.TestUtil.useV2;
import static org.apache.jackrabbit.oak.plugins.nodetype.NodeTypeConstants.JCR_NODE_TYPES;
import static org.junit.Assert.fail;
@@ -38,15 +40,16 @@ import java.util.List;
import javax.annotation.Nonnull;
+import org.apache.jackrabbit.JcrConstants;
import org.apache.jackrabbit.oak.Oak;
import org.apache.jackrabbit.oak.api.ContentRepository;
import org.apache.jackrabbit.oak.api.Root;
import org.apache.jackrabbit.oak.api.Tree;
import org.apache.jackrabbit.oak.core.SystemRoot;
-import org.apache.jackrabbit.oak.plugins.index.aggregate.AggregateIndexProvider;
import org.apache.jackrabbit.oak.plugins.index.aggregate.NodeAggregator;
import org.apache.jackrabbit.oak.plugins.index.aggregate.SimpleNodeAggregator;
import org.apache.jackrabbit.oak.plugins.memory.MemoryNodeStore;
+import org.apache.jackrabbit.oak.plugins.memory.PropertyStates;
import org.apache.jackrabbit.oak.plugins.name.NamespaceEditorProvider;
import org.apache.jackrabbit.oak.plugins.nodetype.TypeEditorProvider;
import org.apache.jackrabbit.oak.plugins.nodetype.write.InitialContent;
@@ -55,11 +58,13 @@ import org.apache.jackrabbit.oak.query.A
import org.apache.jackrabbit.oak.spi.commit.CompositeEditorProvider;
import org.apache.jackrabbit.oak.spi.commit.EditorHook;
import org.apache.jackrabbit.oak.spi.commit.Observer;
+import org.apache.jackrabbit.oak.spi.query.QueryIndexProvider;
import org.apache.jackrabbit.oak.spi.security.OpenSecurityProvider;
import org.apache.jackrabbit.oak.spi.state.ApplyDiff;
import org.apache.jackrabbit.oak.spi.state.NodeBuilder;
import org.apache.jackrabbit.oak.spi.state.NodeState;
import org.apache.jackrabbit.oak.spi.state.NodeStore;
+import org.apache.jackrabbit.oak.util.TreeUtil;
import org.junit.Test;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@@ -120,7 +125,7 @@ public class LuceneIndexAggregationTest2
})
.with(new OpenSecurityProvider())
- .with(AggregateIndexProvider.wrap(provider.with(getNodeAggregator())))
+ .with(((QueryIndexProvider)provider.with(getNodeAggregator())))
.with((Observer) provider).with(new LuceneIndexEditorProvider())
.createContentRepository();
}
@@ -144,7 +149,29 @@ public class LuceneIndexAggregationTest2
@Override
protected void createTestIndexNode() throws Exception {
Tree index = root.getTree("/");
- createTestIndexNode(index, LuceneIndexConstants.TYPE_LUCENE);
+ Tree indexDefn = createTestIndexNode(index, LuceneIndexConstants.TYPE_LUCENE);
+ useV2(indexDefn);
+ //Aggregates
+ newNodeAggregator(indexDefn)
+ .newRuleWithName(NT_FILE, newArrayList("jcr:content"))
+ .newRuleWithName(NT_TEST_PAGE, newArrayList("jcr:content"))
+ .newRuleWithName(NT_TEST_PAGECONTENT, newArrayList("*", "*/*", "*/*/*", "*/*/*/*"))
+ .newRuleWithName(NT_TEST_ASSET, newArrayList("jcr:content"))
+ .newRuleWithName(
+ NT_TEST_ASSETCONTENT,
+ newArrayList("metadata", "renditions", "renditions/original", "comments",
+ "renditions/original/jcr:content"))
+ .newRuleWithName("rep:User", newArrayList("profile"));
+
+ Tree originalInclude = indexDefn.getChild(LuceneIndexConstants.AGGREGATES)
+ .getChild(NT_TEST_ASSET).addChild("includeOriginal");
+ originalInclude.setProperty(LuceneIndexConstants.AGG_RELATIVE_NODE, true);
+ originalInclude.setProperty(LuceneIndexConstants.AGG_PATH, "jcr:content/renditions/original");
+
+ //Include all properties
+ Tree props = TestUtil.newRulePropTree(indexDefn, "test:Asset");
+ TestUtil.enableForFullText(props, "jcr:content/metadata/format");
+ TestUtil.enableForFullText(props, LuceneIndexConstants.REGEX_ALL_PROPS, true);
root.commit();
}
@@ -265,7 +292,41 @@ public class LuceneIndexAggregationTest2
assertQuery(statement, "xpath", expected);
setTraversalEnabled(true);
}
-
+
+ @Test
+ public void indexRelativeNode() throws Exception {
+ setTraversalEnabled(false);
+ final String statement = "//element(*, test:Asset)[ " +
+ "jcr:contains(., 'summer') " +
+ "and jcr:contains(jcr:content/renditions/original, 'fox')" +
+ "and jcr:contains(jcr:content/metadata/@format, 'image') " +
+ "]";
+
+ Tree content = root.getTree("/").addChild("content");
+ List<String> expected = newArrayList();
+
+ Tree metadata = createAssetStructure(content, "tagged");
+ metadata.setProperty("tags", of("namespace:season/summer"), STRINGS);
+ metadata.setProperty("format", "image/jpeg", STRING);
+
+ Tree original = metadata.getParent().addChild("renditions").addChild("original");
+ original.setProperty(JcrConstants.JCR_PRIMARYTYPE, JcrConstants.NT_FILE);
+ original.addChild("jcr:content").setProperty(PropertyStates.createProperty("jcr:data", "fox jumps".getBytes()));
+
+ expected.add("/content/tagged");
+ root.commit();
+
+ assertQuery(statement, "xpath", expected);
+
+ //Update the reaggregated node and with that parent should be get updated
+ Tree originalContent = TreeUtil.getTree(root.getTree("/"), "/content/tagged/jcr:content/renditions/original/jcr:content");
+ originalContent.setProperty(PropertyStates.createProperty("jcr:data", "kiwi jumps".getBytes()));
+ root.commit();
+ assertQuery(statement, "xpath", Collections.<String>emptyList());
+ setTraversalEnabled(true);
+ }
+
+
/**
* <p>
* convenience method that create an "asset" structure like
Modified: jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditorTest.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditorTest.java?rev=1641771&r1=1641770&r2=1641771&view=diff
==============================================================================
--- jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditorTest.java (original)
+++ jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditorTest.java Wed Nov 26 08:06:52 2014
@@ -93,11 +93,15 @@ public class LuceneIndexEditorTest {
tracker.update(indexed);
//system fields starts with ':' so need to be escaped
- assertEquals("/test", query("\\"+FieldNames.createAnalyzedFieldName("foo")+":fox"));
+ assertEquals("/test", query(escape(FieldNames.createAnalyzedFieldName("foo"))+":fox"));
assertNull("Non string properties not indexed by default",
getPath(NumericRangeQuery.newLongRange("price", 100L, 100L, true, true)));
}
+ private String escape(String name) {
+ return name.replace(":", "\\:");
+ }
+
@Test
public void testLuceneWithNonFullText() throws Exception {
NodeBuilder index = builder.child(INDEX_DEFINITIONS_NAME);
Modified: jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexQueryTest.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexQueryTest.java?rev=1641771&r1=1641770&r2=1641771&view=diff
==============================================================================
--- jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexQueryTest.java (original)
+++ jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexQueryTest.java Wed Nov 26 08:06:52 2014
@@ -28,11 +28,13 @@ import org.apache.jackrabbit.oak.query.A
import org.apache.jackrabbit.oak.spi.commit.Observer;
import org.apache.jackrabbit.oak.spi.query.QueryIndexProvider;
import org.apache.jackrabbit.oak.spi.security.OpenSecurityProvider;
+import org.junit.Ignore;
import org.junit.Test;
import static java.util.Arrays.asList;
import static junit.framework.Assert.assertEquals;
import static org.apache.jackrabbit.oak.api.Type.STRINGS;
+import static org.apache.jackrabbit.oak.plugins.index.lucene.TestUtil.useV2;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
@@ -46,8 +48,14 @@ public class LuceneIndexQueryTest extend
protected void createTestIndexNode() throws Exception {
Tree index = root.getTree("/");
Tree indexDefn = createTestIndexNode(index, LuceneIndexConstants.TYPE_LUCENE);
- //TODO Remove compat mode once OAK-2278 resolved
- indexDefn.setProperty(LuceneIndexConstants.COMPAT_MODE, IndexFormatVersion.V1.getVersion());
+ useV2(indexDefn);
+ indexDefn.setProperty(LuceneIndexConstants.TEST_MODE, true);
+ indexDefn.setProperty(LuceneIndexConstants.EVALUATE_PATH_RESTRICTION, true);
+
+ Tree props = TestUtil.newRulePropTree(indexDefn, "nt:base");
+ TestUtil.enablePropertyIndex(props, "c1/p", false);
+ TestUtil.enableForFullText(props, LuceneIndexConstants.REGEX_ALL_PROPS, true);
+
root.commit();
}
@@ -67,6 +75,7 @@ public class LuceneIndexQueryTest extend
test("sql1.txt");
}
+ @Ignore("OAK-2296")
@Test
public void sql2() throws Exception {
test("sql2.txt");
Modified: jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/TestUtil.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/TestUtil.java?rev=1641771&r1=1641770&r2=1641771&view=diff
==============================================================================
--- jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/TestUtil.java (original)
+++ jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/plugins/index/lucene/TestUtil.java Wed Nov 26 08:06:52 2014
@@ -19,7 +19,9 @@
package org.apache.jackrabbit.oak.plugins.index.lucene;
+import java.util.List;
import java.util.Set;
+import java.util.concurrent.atomic.AtomicInteger;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
@@ -29,6 +31,7 @@ import org.apache.jackrabbit.oak.plugins
import org.apache.jackrabbit.oak.spi.state.NodeBuilder;
public class TestUtil {
+ private static final AtomicInteger COUNTER = new AtomicInteger();
static void useV2(NodeBuilder idxNb) {
idxNb.setProperty(LuceneIndexConstants.COMPAT_MODE, IndexFormatVersion.V2.getVersion());
@@ -46,4 +49,62 @@ public class TestUtil {
return nb;
}
+ public static Tree enableForFullText(Tree props, String propName) {
+ return enableForFullText(props, propName, false);
+ }
+
+ public static Tree enableForFullText(Tree props, String propName, boolean regex) {
+ Tree prop = props.addChild(unique("prop"));
+ prop.setProperty(LuceneIndexConstants.PROP_NAME, propName);
+ prop.setProperty(LuceneIndexConstants.PROP_PROPERTY_INDEX, true);
+ prop.setProperty(LuceneIndexConstants.PROP_IS_REGEX, regex);
+ prop.setProperty(LuceneIndexConstants.PROP_NODE_SCOPE_INDEX, true);
+ prop.setProperty(LuceneIndexConstants.PROP_ANALYZED, true);
+ prop.setProperty(LuceneIndexConstants.PROP_USE_IN_EXCERPT, true);
+ return prop;
+ }
+
+ public static Tree enablePropertyIndex(Tree props, String propName, boolean regex) {
+ Tree prop = props.addChild(unique("prop"));
+ prop.setProperty(LuceneIndexConstants.PROP_NAME, propName);
+ prop.setProperty(LuceneIndexConstants.PROP_PROPERTY_INDEX, true);
+ prop.setProperty(LuceneIndexConstants.PROP_IS_REGEX, regex);
+ prop.setProperty(LuceneIndexConstants.PROP_NODE_SCOPE_INDEX, false);
+ prop.setProperty(LuceneIndexConstants.PROP_ANALYZED, false);
+ return prop;
+ }
+
+ public static AggregatorBuilder newNodeAggregator(Tree indexDefn){
+ return new AggregatorBuilder(indexDefn);
+ }
+
+ public static Tree newRulePropTree(Tree indexDefn, String typeName){
+ Tree rules = indexDefn.addChild(LuceneIndexConstants.INDEX_RULES);
+ rules.setOrderableChildren(true);
+ Tree rule = rules.addChild(typeName);
+ Tree props = rule.addChild(LuceneIndexConstants.PROP_NODE);
+ props.setOrderableChildren(true);
+ return props;
+ }
+
+ static class AggregatorBuilder {
+ private final Tree aggs;
+
+ private AggregatorBuilder(Tree indexDefn) {
+ this.aggs = indexDefn.addChild(LuceneIndexConstants.AGGREGATES);
+ }
+
+ AggregatorBuilder newRuleWithName(String primaryType,
+ List<String> includes){
+ Tree agg = aggs.addChild(primaryType);
+ for (String include : includes){
+ agg.addChild(unique("include")).setProperty(LuceneIndexConstants.AGG_PATH, include);
+ }
+ return this;
+ }
+ }
+
+ private static String unique(String name){
+ return name + COUNTER.getAndIncrement();
+ }
}