Author: tommaso
Date: Tue Nov 24 10:38:34 2015
New Revision: 1716100

URL: http://svn.apache.org/viewvc?rev=1716100&view=rev
Log:
OAK-3149 - each index has its own (persisted) suggester if suggest is enabled

Modified:
    
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/FieldFactory.java
    
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexNode.java
    
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndex.java
    
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditor.java
    
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditorContext.java
    
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LucenePropertyIndex.java
    
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/OakDirectory.java
    
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/SuggestHelper.java
    
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/package-info.java
    
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/jcr/query/SuggestTest.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/FieldFactory.java
URL: 
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/FieldFactory.java?rev=1716100&r1=1716099&r2=1716100&view=diff
==============================================================================
--- 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/FieldFactory.java
 (original)
+++ 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/FieldFactory.java
 Tue Nov 24 10:38:34 2015
@@ -134,7 +134,7 @@ public final class FieldFactory {
             }
             builder.append(v);
         }
-        return new OakTextField(FieldNames.SUGGEST, builder.toString(), true);
+        return new OakTextField(FieldNames.SUGGEST, builder.toString(), false);
     }
 
     /**

Modified: 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexNode.java
URL: 
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexNode.java?rev=1716100&r1=1716099&r2=1716100&view=diff
==============================================================================
--- 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexNode.java
 (original)
+++ 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/IndexNode.java
 Tue Nov 24 10:38:34 2015
@@ -30,24 +30,26 @@ import java.util.concurrent.locks.Reentr
 import javax.annotation.Nullable;
 
 import org.apache.jackrabbit.oak.commons.PathUtils;
+import org.apache.jackrabbit.oak.plugins.index.lucene.util.SuggestHelper;
 import org.apache.jackrabbit.oak.spi.state.NodeState;
 import org.apache.jackrabbit.oak.spi.state.ReadOnlyBuilder;
 import org.apache.lucene.index.DirectoryReader;
 import org.apache.lucene.index.IndexReader;
 import org.apache.lucene.search.IndexSearcher;
+import org.apache.lucene.search.suggest.analyzing.AnalyzingInfixSuggester;
 import org.apache.lucene.store.Directory;
 import org.apache.lucene.store.FSDirectory;
 
 class IndexNode {
 
-    static IndexNode open(String indexPath, NodeState root, NodeState 
defnNodeState,@Nullable IndexCopier cloner)
+    static IndexNode open(String indexPath, NodeState root, NodeState 
defnNodeState, @Nullable IndexCopier cloner)
             throws IOException {
         Directory directory = null;
         IndexDefinition definition = new IndexDefinition(root, defnNodeState, 
indexPath);
         NodeState data = defnNodeState.getChildNode(INDEX_DATA_CHILD_NAME);
         if (data.exists()) {
             directory = new OakDirectory(new ReadOnlyBuilder(defnNodeState), 
definition, true);
-            if (cloner != null){
+            if (cloner != null) {
                 directory = cloner.wrapForRead(indexPath, definition, 
directory);
             }
         } else if 
(PERSISTENCE_FILE.equalsIgnoreCase(defnNodeState.getString(PERSISTENCE_NAME))) {
@@ -59,7 +61,12 @@ class IndexNode {
 
         if (directory != null) {
             try {
-                IndexNode index = new IndexNode(PathUtils.getName(indexPath), 
definition, directory);
+                OakDirectory suggestDirectory = null;
+                if (definition.isSuggestEnabled()) {
+                    suggestDirectory = new 
OakDirectory(defnNodeState.builder(), ":suggest-data", definition, false);
+                }
+
+                IndexNode index = new IndexNode(PathUtils.getName(indexPath), 
definition, directory, suggestDirectory);
                 directory = null; // closed in Index.close()
                 return index;
             } finally {
@@ -84,15 +91,22 @@ class IndexNode {
 
     private final ReadWriteLock lock = new ReentrantReadWriteLock();
 
+    private final AnalyzingInfixSuggester lookup;
+
     private boolean closed = false;
 
-    IndexNode(String name, IndexDefinition definition, Directory directory)
+    IndexNode(String name, IndexDefinition definition, Directory directory, 
final OakDirectory suggestDirectory)
             throws IOException {
         this.name = name;
         this.definition = definition;
         this.directory = directory;
         this.reader = DirectoryReader.open(directory);
         this.searcher = new IndexSearcher(reader);
+        if (suggestDirectory != null) {
+            this.lookup = SuggestHelper.getLookup(suggestDirectory, 
definition.getAnalyzer());
+        } else {
+            this.lookup = null;
+        }
     }
 
     String getName() {
@@ -107,6 +121,10 @@ class IndexNode {
         return searcher;
     }
 
+    AnalyzingInfixSuggester getLookup() {
+        return lookup;
+    }
+
     boolean acquire() {
         lock.readLock().lock();
         if (closed) {

Modified: 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndex.java
URL: 
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndex.java?rev=1716100&r1=1716099&r2=1716100&view=diff
==============================================================================
--- 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndex.java
 (original)
+++ 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndex.java
 Tue Nov 24 10:38:34 2015
@@ -412,7 +412,7 @@ public class LuceneIndex implements Adva
                         noDocs = true;
                     } else if (luceneRequestFacade.getLuceneRequest() 
instanceof SuggestHelper.SuggestQuery) {
                         SuggestHelper.SuggestQuery suggestQuery = 
(SuggestHelper.SuggestQuery) luceneRequestFacade.getLuceneRequest();
-                        List<Lookup.LookupResult> lookupResults = 
SuggestHelper.getSuggestions(suggestQuery);
+                        List<Lookup.LookupResult> lookupResults = 
SuggestHelper.getSuggestions(indexNode.getLookup(), suggestQuery);
 
                         // ACL filter suggestions
                         Collection<String> suggestedWords = new 
ArrayList<String>(lookupResults.size());

Modified: 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditor.java
URL: 
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditor.java?rev=1716100&r1=1716099&r2=1716100&view=diff
==============================================================================
--- 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditor.java
 (original)
+++ 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditor.java
 Tue Nov 24 10:38:34 2015
@@ -380,7 +380,7 @@ public class LuceneIndexEditor implement
         // because of LUCENE-5833 we have to merge the suggest fields into a 
single one
         Field suggestField = null;
         for (Field f : fields) {
-            if (FieldNames.SUGGEST.endsWith(f.name())) {
+            if (FieldNames.SUGGEST.equals(f.name())) {
                 if (suggestField == null) {
                     suggestField = 
FieldFactory.newSuggestField(f.stringValue());
                 } else {
@@ -425,7 +425,7 @@ public class LuceneIndexEditor implement
                     }
 
                     if (pd.useInSuggest) {
-                        fields.add(newPropertyField(FieldNames.SUGGEST, value, 
true, true));
+                        fields.add(FieldFactory.newSuggestField(value));
                     }
 
                     if (pd.useInSpellcheck) {

Modified: 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditorContext.java
URL: 
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditorContext.java?rev=1716100&r1=1716099&r2=1716100&view=diff
==============================================================================
--- 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditorContext.java
 (original)
+++ 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LuceneIndexEditorContext.java
 Tue Nov 24 10:38:34 2015
@@ -79,6 +79,7 @@ public class LuceneIndexEditorContext {
             Analyzer definitionAnalyzer = definition.getAnalyzer();
             Map<String, Analyzer> analyzers = new HashMap<String, Analyzer>();
             analyzers.put(FieldNames.SPELLCHECK, new 
ShingleAnalyzerWrapper(LuceneIndexConstants.ANALYZER, 3));
+            analyzers.put(FieldNames.SUGGEST, SuggestHelper.getAnalyzer());
             Analyzer analyzer = new 
PerFieldAnalyzerWrapper(definitionAnalyzer, analyzers);
             IndexWriterConfig config = new IndexWriterConfig(VERSION, 
analyzer);
             if (remoteDir) {
@@ -136,7 +137,6 @@ public class LuceneIndexEditorContext {
     @Nullable
     private final IndexCopier indexCopier;
 
-
     private Directory directory;
 
     private final TextExtractionStats textExtractionStats = new 
TextExtractionStats();
@@ -190,12 +190,12 @@ public class LuceneIndexEditorContext {
         checkNotNull(writer);
         checkNotNull(definition);
         checkNotNull(directory);
-        
+
         int docs = writer.numDocs();
         int ram = writer.numRamDocs();
 
         log.trace("Writer for direcory {} - docs: {}, ramDocs: {}", 
definition, docs, ram);
-        
+
         String[] files = directory.listAll();
         long overallSize = 0;
         StringBuilder sb = new StringBuilder();
@@ -231,18 +231,18 @@ public class LuceneIndexEditorContext {
             if (log.isTraceEnabled()) {
                 trackIndexSizeInfo(writer, definition, directory);
             }
-            
+
             final long start = PERF_LOGGER.start();
-            
-            updateSuggester();
+
+            updateSuggester(writer.getAnalyzer());
             PERF_LOGGER.end(start, -1, "Completed suggester for directory {}", 
definition);
-            
+
             writer.close();
             PERF_LOGGER.end(start, -1, "Closed writer for directory {}", 
definition);
-            
+
             directory.close();
             PERF_LOGGER.end(start, -1, "Closed directory for directory {}", 
definition);
-            
+
             //OAK-2029 Record the last updated status so
             //as to make IndexTracker detect changes when index
             //is stored in file system
@@ -250,7 +250,7 @@ public class LuceneIndexEditorContext {
             status.setProperty("lastUpdated", 
ISO8601.format(Calendar.getInstance()), Type.DATE);
             status.setProperty("indexedNodes",indexedNodes);
             PERF_LOGGER.end(start, -1, "Overall Closed IndexWriter for 
directory {}", definition);
-            
+
             textExtractionStats.log(reindex);
             textExtractionStats.collectStats(extractedTextCache);
         }
@@ -259,8 +259,9 @@ public class LuceneIndexEditorContext {
     /**
      * eventually update suggest dictionary
      * @throws IOException if suggest dictionary update fails
+     * @param analyzer the analyzer used to update the suggester
      */
-    private void updateSuggester() throws IOException {
+    private void updateSuggester(Analyzer analyzer) throws IOException {
 
         if (definition.isSuggestEnabled()) {
 
@@ -280,12 +281,14 @@ public class LuceneIndexEditorContext {
 
             if (updateSuggester) {
                 DirectoryReader reader = DirectoryReader.open(writer, false);
+                final OakDirectory suggestDirectory = new 
OakDirectory(definitionBuilder, ":suggest-data", definition, false);
                 try {
-                    SuggestHelper.updateSuggester(reader);
+                    SuggestHelper.updateSuggester(suggestDirectory, analyzer, 
reader);
                     suggesterStatus.setProperty("lastUpdated", 
ISO8601.format(Calendar.getInstance()), Type.DATE);
                 } catch (Throwable e) {
                     log.warn("could not update suggester", e);
                 } finally {
+                    suggestDirectory.close();
                     reader.close();
                 }
             }

Modified: 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LucenePropertyIndex.java
URL: 
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LucenePropertyIndex.java?rev=1716100&r1=1716099&r2=1716100&view=diff
==============================================================================
--- 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LucenePropertyIndex.java
 (original)
+++ 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/LucenePropertyIndex.java
 Tue Nov 24 10:38:34 2015
@@ -32,7 +32,6 @@ import java.util.Set;
 import java.util.concurrent.atomic.AtomicReference;
 
 import com.google.common.collect.AbstractIterator;
-import com.google.common.collect.Iterables;
 import com.google.common.collect.Lists;
 import com.google.common.collect.Queues;
 import com.google.common.collect.Sets;
@@ -78,6 +77,7 @@ import org.apache.lucene.index.MultiFiel
 import org.apache.lucene.index.StoredFieldVisitor;
 import org.apache.lucene.index.Term;
 import org.apache.lucene.queries.CustomScoreQuery;
+import org.apache.lucene.queryparser.classic.MultiFieldQueryParser;
 import org.apache.lucene.queryparser.classic.ParseException;
 import org.apache.lucene.queryparser.classic.QueryParser;
 import org.apache.lucene.queryparser.flexible.core.QueryNodeException;
@@ -406,13 +406,14 @@ public class LucenePropertyIndex impleme
                             }
                         }
                     } else if (luceneRequestFacade.getLuceneRequest() 
instanceof SpellcheckHelper.SpellcheckQuery) {
+                        String aclCheckField = 
indexNode.getDefinition().isFullTextEnabled() ? FieldNames.FULLTEXT : 
FieldNames.SPELLCHECK;
                         SpellcheckHelper.SpellcheckQuery spellcheckQuery = 
(SpellcheckHelper.SpellcheckQuery) luceneRequestFacade.getLuceneRequest();
                         SuggestWord[] suggestWords = 
SpellcheckHelper.getSpellcheck(spellcheckQuery);
 
                         // ACL filter spellchecks
-                        QueryParser qp = new QueryParser(Version.LUCENE_47, 
FieldNames.FULLTEXT, indexNode.getDefinition().getAnalyzer());
+                        QueryParser qp = new QueryParser(Version.LUCENE_47, 
aclCheckField, indexNode.getDefinition().getAnalyzer());
                         for (SuggestWord suggestion : suggestWords) {
-                            Query query = 
qp.createPhraseQuery(FieldNames.FULLTEXT, suggestion.string);
+                            Query query = qp.createPhraseQuery(aclCheckField, 
suggestion.string);
                             TopDocs topDocs = searcher.search(query, 100);
                             if (topDocs.totalHits > 0) {
                                 for (ScoreDoc doc : topDocs.scoreDocs) {
@@ -429,12 +430,13 @@ public class LucenePropertyIndex impleme
                     } else if (luceneRequestFacade.getLuceneRequest() 
instanceof SuggestHelper.SuggestQuery) {
                         SuggestHelper.SuggestQuery suggestQuery = 
(SuggestHelper.SuggestQuery) luceneRequestFacade.getLuceneRequest();
 
-                        List<Lookup.LookupResult> lookupResults = 
SuggestHelper.getSuggestions(suggestQuery);
+                        List<Lookup.LookupResult> lookupResults = 
SuggestHelper.getSuggestions(indexNode.getLookup(), suggestQuery);
 
+                        Collection<String> indexedFields = 
MultiFields.getIndexedFields(searcher.getIndexReader());
+                        QueryParser qp = new 
MultiFieldQueryParser(Version.LUCENE_47, indexedFields.toArray(new 
String[indexedFields.size()]), indexNode.getDefinition().getAnalyzer());
                         // ACL filter suggestions
-                        QueryParser qp = new QueryParser(Version.LUCENE_47, 
FieldNames.SUGGEST, indexNode.getDefinition().getAnalyzer());
                         for (Lookup.LookupResult suggestion : lookupResults) {
-                            Query query = 
qp.createPhraseQuery(FieldNames.SUGGEST, suggestion.key.toString());
+                            Query query = qp.parse("\"" + 
suggestion.key.toString() + "\"");
                             TopDocs topDocs = searcher.search(query, 100);
                             if (topDocs.totalHits > 0) {
                                 for (ScoreDoc doc : topDocs.scoreDocs) {
@@ -449,7 +451,7 @@ public class LucenePropertyIndex impleme
 
                         noDocs = true;
                     }
-                } catch (IOException e) {
+                } catch (Exception e) {
                     LOG.warn("query via {} failed.", LucenePropertyIndex.this, 
e);
                 } finally {
                     indexNode.release();

Modified: 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/OakDirectory.java
URL: 
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/OakDirectory.java?rev=1716100&r1=1716099&r2=1716100&view=diff
==============================================================================
--- 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/OakDirectory.java
 (original)
+++ 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/OakDirectory.java
 Tue Nov 24 10:38:34 2015
@@ -84,9 +84,13 @@ class OakDirectory extends Directory {
     private final boolean activeDeleteEnabled;
 
     public OakDirectory(NodeBuilder builder, IndexDefinition definition, 
boolean readOnly) {
+        this(builder, INDEX_DATA_CHILD_NAME, definition, readOnly);
+    }
+
+    public OakDirectory(NodeBuilder builder, String dataNodeName, 
IndexDefinition definition, boolean readOnly) {
         this.lockFactory = NoLockFactory.getNoLockFactory();
         this.builder = builder;
-        this.directoryBuilder = builder.child(INDEX_DATA_CHILD_NAME);
+        this.directoryBuilder = builder.child(dataNodeName);
         this.definition = definition;
         this.readOnly = readOnly;
         this.fileNames.addAll(getListing());

Modified: 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/SuggestHelper.java
URL: 
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/SuggestHelper.java?rev=1716100&r1=1716099&r2=1716100&view=diff
==============================================================================
--- 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/SuggestHelper.java
 (original)
+++ 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/SuggestHelper.java
 Tue Nov 24 10:38:34 2015
@@ -18,17 +18,22 @@
  */
 package org.apache.jackrabbit.oak.plugins.index.lucene.util;
 
+import java.io.File;
 import java.io.IOException;
 import java.io.Reader;
 import java.util.Collections;
 import java.util.List;
 
+import com.google.common.io.Files;
 import org.apache.jackrabbit.oak.plugins.index.lucene.FieldNames;
 import org.apache.lucene.analysis.Analyzer;
 import org.apache.lucene.index.IndexReader;
-import org.apache.lucene.search.suggest.DocumentDictionary;
+import org.apache.lucene.search.spell.Dictionary;
+import org.apache.lucene.search.spell.LuceneDictionary;
 import org.apache.lucene.search.suggest.Lookup;
-import org.apache.lucene.search.suggest.analyzing.FreeTextSuggester;
+import org.apache.lucene.search.suggest.analyzing.AnalyzingInfixSuggester;
+import org.apache.lucene.store.Directory;
+import org.apache.lucene.store.FSDirectory;
 import org.apache.lucene.util.Version;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -48,29 +53,20 @@ public class SuggestHelper {
         }
     };
 
-    private static final Lookup suggester = new FreeTextSuggester(analyzer);
-
-    public static void updateSuggester(IndexReader reader) throws IOException {
-//        Terms terms = MultiFields.getTerms(reader, FieldNames.SUGGEST);
-//        long size = terms.size() * 2;
-//        if (size < 0) {
-//            size = terms.getDocCount() / 3;
-//        }
-//        long count = suggester.getCount();
-//        if (size  > count) {
-            try {
-                suggester.build(new DocumentDictionary(reader, 
FieldNames.SUGGEST, FieldNames.PATH_DEPTH));
-            } catch (RuntimeException e) {
-                log.debug("could not update the suggester", e);
-            }
-//        }
+    public static void updateSuggester(Directory directory, Analyzer analyzer, 
IndexReader reader) throws IOException {
+        try {
+            Dictionary dictionary = new LuceneDictionary(reader, 
FieldNames.SUGGEST);
+            getLookup(directory, analyzer).build(dictionary);
+        } catch (RuntimeException e) {
+            log.debug("could not update the suggester", e);
+        }
     }
 
-    public static List<Lookup.LookupResult> getSuggestions(SuggestQuery 
suggestQuery) {
+    public static List<Lookup.LookupResult> 
getSuggestions(AnalyzingInfixSuggester suggester, SuggestQuery suggestQuery) {
         try {
             long count = suggester.getCount();
             if (count > 0) {
-                return suggester.lookup(suggestQuery.getText(), false, 10);
+                return suggester.lookup(suggestQuery.getText(), 10, true, 
false);
             } else {
                 return Collections.emptyList();
             }
@@ -103,6 +99,28 @@ public class SuggestHelper {
         }
     }
 
+    public static AnalyzingInfixSuggester getLookup(final Directory 
suggestDirectory) throws IOException {
+        return getLookup(suggestDirectory, SuggestHelper.analyzer);
+    }
+
+    public static AnalyzingInfixSuggester getLookup(final Directory 
suggestDirectory, Analyzer analyzer) throws IOException {
+        final File tempDir = Files.createTempDir();
+        return new AnalyzingInfixSuggester(Version.LUCENE_47, tempDir, 
analyzer, analyzer, 3) {
+            @Override
+            protected Directory getDirectory(File path) throws IOException {
+                if (tempDir.getAbsolutePath().equals(path.getAbsolutePath())) {
+                    return suggestDirectory; // use oak directory for writing 
suggest index
+                } else {
+                    return FSDirectory.open(path); // use FS for temp index 
used at build time
+                }
+            }
+        };
+    }
+
+    public static Analyzer getAnalyzer() {
+        return analyzer;
+    }
+
     public static class SuggestQuery {
 
         private final String text;

Modified: 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/package-info.java
URL: 
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/package-info.java?rev=1716100&r1=1716099&r2=1716100&view=diff
==============================================================================
--- 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/package-info.java
 (original)
+++ 
jackrabbit/oak/trunk/oak-lucene/src/main/java/org/apache/jackrabbit/oak/plugins/index/lucene/util/package-info.java
 Tue Nov 24 10:38:34 2015
@@ -14,7 +14,7 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-@Version("1.2.0")
+@Version("2.0.0")
 @Export(optional = "provide:=true")
 package org.apache.jackrabbit.oak.plugins.index.lucene.util;
 

Modified: 
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/jcr/query/SuggestTest.java
URL: 
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/jcr/query/SuggestTest.java?rev=1716100&r1=1716099&r2=1716100&view=diff
==============================================================================
--- 
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/jcr/query/SuggestTest.java
 (original)
+++ 
jackrabbit/oak/trunk/oak-lucene/src/test/java/org/apache/jackrabbit/oak/jcr/query/SuggestTest.java
 Tue Nov 24 10:38:34 2015
@@ -90,6 +90,22 @@ public class SuggestTest extends Abstrac
         assertTrue(result.contains("in 2015 my fox is red, like mike's fox and 
john's fox"));
     }
 
+    public void testSuggestInfix() throws Exception {
+        Session session = superuser;
+        QueryManager qm = session.getWorkspace().getQueryManager();
+        Node n1 = testRootNode.addNode("node1");
+        n1.setProperty("jcr:title", "in 2015 my fox is red, like mike's fox 
and john's fox");
+        Node n2 = testRootNode.addNode("node2");
+        n2.setProperty("jcr:title", "in 2015 a red fox is still a fox");
+        session.save();
+
+        String xpath = "/jcr:root[rep:suggest('like mike')]/(rep:suggest())";
+        Query q = qm.createQuery(xpath, Query.XPATH);
+        List<String> result = getResult(q.execute(), "rep:suggest()");
+        assertNotNull(result);
+        assertTrue(result.contains("in 2015 my fox is red, like mike's fox and 
john's fox"));
+    }
+
     public void testNoSuggestions() throws Exception {
         Session session = superuser;
         QueryManager qm = session.getWorkspace().getQueryManager();

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=1716100&r1=1716099&r2=1716100&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
 Tue Nov 24 10:38:34 2015
@@ -460,11 +460,11 @@ public class IndexPlannerTest {
     }
 
     private IndexNode createIndexNode(IndexDefinition defn, long numOfDocs) 
throws IOException {
-        return new IndexNode("foo", defn, createSampleDirectory(numOfDocs));
+        return new IndexNode("foo", defn, createSampleDirectory(numOfDocs), 
null);
     }
 
     private IndexNode createIndexNode(IndexDefinition defn) throws IOException 
{
-        return new IndexNode("foo", defn, createSampleDirectory());
+        return new IndexNode("foo", defn, createSampleDirectory(), null);
     }
 
     private FilterImpl createFilter(String nodeTypeName) {


Reply via email to