예제 #1
0
        public void Can_Add_Doc_With_Fields()
        {
            using (var luceneDir = new RandomIdRAMDirectory())
                using (var indexer = new TestIndex(luceneDir, new StandardAnalyzer(Version.LUCENE_30)))
                {
                    indexer.IndexItem(new ValueSet(1.ToString(), "content", "test",
                                                   new Dictionary <string, IEnumerable <object> >
                    {
                        { "item1", new List <object>(new[] { "value1" }) },
                        { "item2", new List <object>(new[] { "value2" }) }
                    }));


                    using (var s = (LuceneSearcher)indexer.GetSearcher())
                    {
                        var luceneSearcher = s.GetLuceneSearcher();
                        var fields         = luceneSearcher.Doc(0).GetFields().ToArray();
                        Assert.IsNotNull(fields.SingleOrDefault(x => x.Name == "item1"));
                        Assert.IsNotNull(fields.SingleOrDefault(x => x.Name == "item2"));
                        Assert.IsNotNull(fields.SingleOrDefault(x => x.Name == LuceneIndex.ItemTypeFieldName));
                        Assert.IsNotNull(fields.SingleOrDefault(x => x.Name == LuceneIndex.ItemIdFieldName));
                        Assert.IsNotNull(fields.SingleOrDefault(x => x.Name == LuceneIndex.CategoryFieldName));

                        Assert.AreEqual("value1", fields.Single(x => x.Name == "item1").StringValue);
                        Assert.AreEqual("value2", fields.Single(x => x.Name == "item2").StringValue);
                        Assert.AreEqual("test", fields.Single(x => x.Name == LuceneIndex.ItemTypeFieldName).StringValue);
                        Assert.AreEqual("1", fields.Single(x => x.Name == LuceneIndex.ItemIdFieldName).StringValue);
                        Assert.AreEqual("content", fields.Single(x => x.Name == LuceneIndex.CategoryFieldName).StringValue);
                    }
                }
        }
예제 #2
0
        public void Number_Field()
        {
            using (var luceneDir = new RandomIdRAMDirectory())
                using (var indexer = new TestIndex(
                           new FieldDefinitionCollection(new FieldDefinition("item2", "number")),
                           luceneDir,
                           new StandardAnalyzer(Version.LUCENE_30)))
                {
                    indexer.IndexItem(new ValueSet(1.ToString(), "content",
                                                   new Dictionary <string, IEnumerable <object> >
                    {
                        { "item1", new List <object>(new[] { "value1" }) },
                        { "item2", new List <object>(new object[] { 123456 }) }
                    }));

                    using (var s = (LuceneSearcher)indexer.GetSearcher())
                    {
                        var luceneSearcher = s.GetLuceneSearcher();
                        var fields         = luceneSearcher.Doc(luceneSearcher.MaxDoc - 1).GetFields().ToArray();

                        var valType = indexer.FieldValueTypeCollection.GetValueType("item2");
                        Assert.AreEqual(typeof(Int32Type), valType.GetType());
                        Assert.IsNotNull(fields.SingleOrDefault(x => x.Name == "item2"));
                    }
                }
        }
예제 #3
0
        private void DoSpatialSearch(
            SpatialContext ctx, SpatialStrategy strategy,
            TestIndex indexer, double searchRadius, string idToMatch, Func <SpatialArgs, Query> createQuery, int lat,
            int lng)
        {
            var searcher       = (LuceneSearcher)indexer.GetSearcher();
            var luceneSearcher = searcher.GetLuceneSearcher();

            GetXYFromCoords(lat, lng, out var x, out var y);

            // Make a circle around the search point
            var args = new SpatialArgs(
                SpatialOperation.Intersects,
                ctx.MakeCircle(x, y, DistanceUtils.Dist2Degrees(searchRadius, DistanceUtils.EARTH_MEAN_RADIUS_KM)));

            var filter = strategy.MakeFilter(args);

            var query = createQuery(args);

            // TODO: It doesn't make a whole lot of sense to sort by score when searching on only geo-coords,
            // typically you would sort by closest distance
            // Which can be done, see https://github.com/apache/lucene-solr/blob/branch_4x/lucene/spatial/src/test/org/apache/lucene/spatial/SpatialExample.java#L169
            TopDocs docs = luceneSearcher.Search(query, filter, MaxResultDocs, new Sort(new SortField(null, SortField.SCORE)));

            AssertDocMatchedIds(luceneSearcher, docs, idToMatch);


            // TODO: We should make this possible and allow passing in a Lucene Filter
            // to the LuceneSearchQuery along with the Lucene Query, then we
            // don't need to manually perform the Lucene Search

            //var criteria = (LuceneSearchQuery)searcher.CreateQuery();
            //criteria.LuceneQuery(q);
            //var results = criteria.Execute();
        }
예제 #4
0
        public void Can_Add_Doc_With_Easy_Fields()
        {
            using (var luceneDir = new RandomIdRAMDirectory())
                using (var indexer = new TestIndex(luceneDir, new StandardAnalyzer(Version.LUCENE_30)))
                {
                    indexer.IndexItem(ValueSet.FromObject(1.ToString(), "content",
                                                          new { item1 = "value1", item2 = "value2" }));

                    using (var s = (LuceneSearcher)indexer.GetSearcher())
                    {
                        var luceneSearcher = s.GetLuceneSearcher();
                        var fields         = luceneSearcher.Doc(0).GetFields().ToArray();
                        Assert.IsNotNull(fields.SingleOrDefault(x => x.Name == "item1"));
                        Assert.IsNotNull(fields.SingleOrDefault(x => x.Name == "item2"));
                        Assert.AreEqual("value1", fields.Single(x => x.Name == "item1").StringValue);
                        Assert.AreEqual("value2", fields.Single(x => x.Name == "item2").StringValue);
                    }
                }
        }
        public void Track_Readers()
        {
            var analyzer = new StandardAnalyzer(Version.LUCENE_30);

            using (var luceneDir = new RandomIdRAMDirectory())
                using (var indexer = new TestIndex(luceneDir, analyzer))
                {
                    indexer.IndexItems(new[] {
                        ValueSet.FromObject(1.ToString(), "content",
                                            new { nodeName = "umbraco", headerText = "world", writerName = "administrator" }),
                        ValueSet.FromObject(2.ToString(), "content",
                                            new { nodeName = "umbraco", headerText = "umbraco", writerName = "administrator" }),
                        ValueSet.FromObject(3.ToString(), "content",
                                            new { nodeName = "umbraco", headerText = "umbraco", writerName = "administrator" }),
                        ValueSet.FromObject(4.ToString(), "content",
                                            new { nodeName = "hello", headerText = "world", writerName = "blah" })
                    });

                    LuceneSearcher searcher       = (LuceneSearcher)indexer.GetSearcher();
                    IndexSearcher  luceneSearcher = (IndexSearcher)searcher.GetLuceneSearcher();

                    //Arrange
                    var sc = searcher.CreateQuery("content").Field("writerName", "administrator");

                    //Act
                    var results = sc.Execute();

                    using (var e1 = results.GetEnumerator())
                    {
                        Assert.AreEqual(2, luceneSearcher.IndexReader.RefCount);
                        using (var e2 = results.Skip(2).GetEnumerator())
                        {
                            Assert.AreEqual(3, luceneSearcher.IndexReader.RefCount);
                        }
                        Assert.AreEqual(2, luceneSearcher.IndexReader.RefCount);
                    }
                    Assert.AreEqual(1, luceneSearcher.IndexReader.RefCount);
                }
        }
예제 #6
0
        public void Can_Have_Multiple_Values_In_Fields()
        {
            using (var luceneDir = new RandomIdRAMDirectory())
                using (var indexer = new TestIndex(luceneDir, new StandardAnalyzer(Version.LUCENE_30)))
                {
                    indexer.IndexItem(new ValueSet(1.ToString(), "content",
                                                   new Dictionary <string, IEnumerable <object> >
                    {
                        {
                            "item1", new List <object> {
                                "subval1", "subval2"
                            }
                        },
                        {
                            "item2", new List <object> {
                                "subval1", "subval2", "subval3"
                            }
                        }
                    }));

                    using (var s = (LuceneSearcher)indexer.GetSearcher())
                    {
                        var luceneSearcher = s.GetLuceneSearcher();
                        var fields         = luceneSearcher.Doc(0).GetFields().ToArray();
                        Assert.AreEqual(2, fields.Count(x => x.Name == "item1"));
                        Assert.AreEqual(3, fields.Count(x => x.Name == "item2"));

                        Assert.AreEqual("subval1", fields.Where(x => x.Name == "item1").ElementAt(0).StringValue);
                        Assert.AreEqual("subval2", fields.Where(x => x.Name == "item1").ElementAt(1).StringValue);

                        Assert.AreEqual("subval1", fields.Where(x => x.Name == "item2").ElementAt(0).StringValue);
                        Assert.AreEqual("subval2", fields.Where(x => x.Name == "item2").ElementAt(1).StringValue);
                        Assert.AreEqual("subval3", fields.Where(x => x.Name == "item2").ElementAt(2).StringValue);
                    }
                }
        }
예제 #7
0
        public void Index_Read_And_Write_Ensure_No_Errors_In_Async()
        {
            using (var d = new RandomIdRAMDirectory())
                using (var writer = new IndexWriter(d, new CultureInvariantStandardAnalyzer(Version.LUCENE_30), IndexWriter.MaxFieldLength.LIMITED))
                    using (var customIndexer = new TestIndex(writer))
                        using (var customSearcher = (LuceneSearcher)customIndexer.GetSearcher())
                        {
                            var waitHandle = new ManualResetEvent(false);

                            void OperationComplete(object sender, IndexOperationEventArgs e)
                            {
                                //signal that we are done
                                waitHandle.Set();
                            }

                            //add the handler for optimized since we know it will be optimized last based on the commit count
                            customIndexer.IndexOperationComplete += OperationComplete;

                            //remove the normal indexing error handler
                            customIndexer.IndexingError -= IndexInitializer.IndexingError;

                            //run in async mode
                            customIndexer.RunAsync = false;

                            //get a node from the data repo
                            var node = _contentService.GetPublishedContentByXPath("//*[string-length(@id)>0 and number(@id)>0]")
                                       .Root
                                       .Elements()
                                       .First();

                            var idQueue              = new ConcurrentQueue <int>(Enumerable.Range(1, 10));
                            var searchThreadCount    = 500;
                            var indexThreadCount     = 10;
                            var searchCount          = 10700;
                            var indexCount           = 100;
                            var searchCountPerThread = Convert.ToInt32(searchCount / searchThreadCount);
                            var indexCountPerThread  = Convert.ToInt32(indexCount / indexThreadCount);

                            //spawn a bunch of threads to perform some reading
                            var tasks = new List <Task>();

                            Action <ISearcher> doSearch = (s) =>
                            {
                                try
                                {
                                    for (var counter = 0; counter < searchCountPerThread; counter++)
                                    {
                                        //get next id and put it to the back of the list
                                        int docId;
                                        if (idQueue.TryDequeue(out docId))
                                        {
                                            idQueue.Enqueue(docId);
                                            var r = s.CreateQuery().Id(docId.ToString()).Execute();
                                            Debug.WriteLine("searching thread: {0}, id: {1}, found: {2}", Thread.CurrentThread.ManagedThreadId, docId, r.Count());
                                            Thread.Sleep(50);
                                        }
                                    }
                                }
                                catch (Exception ex)
                                {
                                    Debug.WriteLine("ERROR!! {0}", ex);
                                    throw;
                                }
                            };

                            Action <IIndex> doIndex = (ind) =>
                            {
                                try
                                {
                                    //reindex the same node a bunch of times
                                    for (var i = 0; i < indexCountPerThread; i++)
                                    {
                                        //get next id and put it to the back of the list
                                        int docId;
                                        if (idQueue.TryDequeue(out docId))
                                        {
                                            idQueue.Enqueue(docId);

                                            var cloned = new XElement(node);
                                            cloned.Attribute("id").Value = docId.ToString(CultureInfo.InvariantCulture);
                                            Debug.WriteLine("Indexing {0}", docId);
                                            ind.IndexItems(new[] { cloned.ConvertToValueSet(IndexTypes.Content) });
                                            Thread.Sleep(100);
                                        }
                                    }
                                }
                                catch (Exception ex)
                                {
                                    Debug.WriteLine("ERROR!! {0}", ex);
                                    throw;
                                }
                            };

                            //indexing threads
                            for (var i = 0; i < indexThreadCount; i++)
                            {
                                var indexer = customIndexer;
                                tasks.Add(Task.Factory.StartNew(() => doIndex(indexer), TaskCreationOptions.LongRunning));
                            }

                            //searching threads
                            for (var i = 0; i < searchThreadCount; i++)
                            {
                                var searcher = customSearcher;
                                tasks.Add(Task.Factory.StartNew(() => doSearch(searcher), TaskCreationOptions.LongRunning));
                            }

                            try
                            {
                                Task.WaitAll(tasks.ToArray());
                            }
                            catch (AggregateException e)
                            {
                                var sb = new StringBuilder();
                                sb.Append(e.Message + ": ");
                                foreach (var v in e.InnerExceptions)
                                {
                                    sb.Append(v.Message + "; ");
                                }
                                Assert.Fail(sb.ToString());
                            }

                            //reset the async mode and remove event handler
                            customIndexer.IndexingError += IndexInitializer.IndexingError;
                            customIndexer.RunAsync       = false;

                            //wait until we are done
                            waitHandle.WaitOne();

                            writer.WaitForMerges();

                            var results = customSearcher.CreateQuery().Field("nodeName", (IExamineValue) new ExamineValue(Examineness.Explicit, "Home")).Execute();
                            Assert.AreEqual(10, results.Count());
                        }
        }
예제 #8
0
        public void Index_Ensure_No_Duplicates_In_Async()
        {
            using (var d = new RandomIdRAMDirectory())
                using (var writer = new IndexWriter(d, new CultureInvariantStandardAnalyzer(Version.LUCENE_30), IndexWriter.MaxFieldLength.LIMITED))
                    using (var customIndexer = new TestIndex(writer))
                    //using (var customSearcher = (LuceneSearcher)customIndexer.GetSearcher())
                    {
                        var waitHandle = new ManualResetEvent(false);

                        void OperationComplete(object sender, IndexOperationEventArgs e)
                        {
                            //signal that we are done
                            waitHandle.Set();
                        }

                        //add the handler for optimized since we know it will be optimized last based on the commit count
                        customIndexer.IndexOperationComplete += OperationComplete;

                        //remove the normal indexing error handler
                        customIndexer.IndexingError -= IndexInitializer.IndexingError;

                        //run in async mode
                        customIndexer.RunAsync = true;

                        //get a node from the data repo
                        var idQueue = new ConcurrentQueue <int>(Enumerable.Range(1, 3));
                        var node    = _contentService.GetPublishedContentByXPath("//*[string-length(@id)>0 and number(@id)>0]")
                                      .Root
                                      .Elements()
                                      .First();

                        //reindex the same nodes a bunch of times
                        for (var i = 0; i < idQueue.Count * 20; i++)
                        {
                            //get next id and put it to the back of the list
                            int docId;
                            if (idQueue.TryDequeue(out docId))
                            {
                                idQueue.Enqueue(docId);

                                var cloned = new XElement(node);
                                cloned.Attribute("id").Value = docId.ToString(CultureInfo.InvariantCulture);
                                Debug.WriteLine("Indexing {0}", docId);
                                customIndexer.IndexItems(new[] { cloned.ConvertToValueSet(IndexTypes.Content) });
                                Thread.Sleep(100);
                            }
                        }

                        //reset the async mode and remove event handler
                        customIndexer.IndexingError += IndexInitializer.IndexingError;
                        customIndexer.RunAsync       = false;

                        //wait until we are done
                        waitHandle.WaitOne();

                        writer.WaitForMerges();

                        //ensure no duplicates

                        var customSearcher = (LuceneSearcher)customIndexer.GetSearcher();
                        var results        = customSearcher.CreateQuery().Field("nodeName", (IExamineValue) new ExamineValue(Examineness.Explicit, "Home")).Execute();
                        Assert.AreEqual(3, results.Count());
                    }
        }
예제 #9
0
        public void Can_Overwrite_Index_During_Indexing_Operation()
        {
            const int ThreadCount = 1000;

            using (var d = new RandomIdRAMDirectory())
                using (var writer = new IndexWriter(d, new CultureInvariantStandardAnalyzer(Version.LUCENE_30), IndexWriter.MaxFieldLength.LIMITED))
                    using (var customIndexer = new TestIndex(writer))
                        using (var customSearcher = (LuceneSearcher)customIndexer.GetSearcher())
                        {
                            var waitHandle = new ManualResetEvent(false);

                            var opCompleteCount = 0;
                            void OperationComplete(object sender, IndexOperationEventArgs e)
                            {
                                Interlocked.Increment(ref opCompleteCount);

                                Console.WriteLine($"OperationComplete: {opCompleteCount}");

                                if (opCompleteCount == ThreadCount)
                                {
                                    //signal that we are done
                                    waitHandle.Set();
                                }
                            }

                            //add the handler for optimized since we know it will be optimized last based on the commit count
                            customIndexer.IndexOperationComplete += OperationComplete;

                            //remove the normal indexing error handler
                            customIndexer.IndexingError -= IndexInitializer.IndexingError;

                            //run in async mode
                            customIndexer.RunAsync = true;

                            //get a node from the data repo
                            var node = _contentService.GetPublishedContentByXPath("//*[string-length(@id)>0 and number(@id)>0]")
                                       .Root
                                       .Elements()
                                       .First();

                            //get the id for th node we're re-indexing.
                            var id = (int)node.Attribute("id");

                            //spawn a bunch of threads to perform some reading
                            var tasks = new List <Task>();

                            //reindex the same node a bunch of times - then while this is running we'll overwrite below
                            for (var i = 0; i < ThreadCount; i++)
                            {
                                var indexer = customIndexer;
                                tasks.Add(Task.Factory.StartNew(() =>
                                {
                                    //get next id and put it to the back of the list
                                    int docId  = i;
                                    var cloned = new XElement(node);
                                    Debug.WriteLine("Indexing {0}", docId);
                                    indexer.IndexItem(cloned.ConvertToValueSet(IndexTypes.Content));
                                }, TaskCreationOptions.LongRunning));
                            }

                            Thread.Sleep(100);

                            //overwrite!
                            customIndexer.EnsureIndex(true);

                            try
                            {
                                Task.WaitAll(tasks.ToArray());
                            }
                            catch (AggregateException e)
                            {
                                var sb = new StringBuilder();
                                sb.Append(e.Message + ": ");
                                foreach (var v in e.InnerExceptions)
                                {
                                    sb.Append(v.Message + "; ");
                                }
                                Assert.Fail(sb.ToString());
                            }

                            //reset the async mode and remove event handler
                            customIndexer.IndexingError += IndexInitializer.IndexingError;
                            customIndexer.RunAsync       = false;

                            //wait until we are done
                            waitHandle.WaitOne(TimeSpan.FromMinutes(2));

                            writer.WaitForMerges();

                            //ensure no data since it's a new index
                            var results = customSearcher.CreateQuery().Field("nodeName", (IExamineValue) new ExamineValue(Examineness.Explicit, "Home")).Execute();

                            //the total times that OperationComplete event should be fired is 1000
                            Assert.AreEqual(1000, opCompleteCount);

                            //should be less than the total inserted because we overwrote it in the middle of processing
                            Debug.WriteLine("TOTAL RESULTS: " + results.TotalItemCount);
                            Assert.Less(results.Count(), 1000);
                        }
        }
예제 #10
0
        public void Index_Read_And_Write_Ensure_No_Errors_In_Async(
            int indexCount,
            int searchCount,
            int indexThreadCount,
            int searchThreadCount,
            int indexThreadWait,
            int searchThreadWait,
            bool inMemory)
        {
            // TODO: In this test can we ensure all readers are tracked and closed?
            // TODO: In the search part, we should be searching in various ways and also with skip

            DirectoryInfo temp = null;

            Lucene.Net.Store.Directory directory;
            if (inMemory)
            {
                directory = new RandomIdRAMDirectory();
            }
            else
            {
                // try to clear out old files
                var tempBasePath = Path.Combine(Path.GetTempPath(), "ExamineTests");
                if (System.IO.Directory.Exists(tempBasePath))
                {
                    try
                    {
                        System.IO.Directory.Delete(tempBasePath, true);
                    }
                    catch
                    {
                    }
                }

                var tempPath = Path.Combine(tempBasePath, Guid.NewGuid().ToString());
                System.IO.Directory.CreateDirectory(tempPath);
                temp      = new DirectoryInfo(tempPath);
                directory = new SimpleFSDirectory(temp);
            }

            try
            {
                using (var d = directory)
                    using (var writer = new IndexWriter(d, new CultureInvariantStandardAnalyzer(Version.LUCENE_30), IndexWriter.MaxFieldLength.LIMITED))
                        using (var customIndexer = new TestIndex(writer))
                            using (var customSearcher = (LuceneSearcher)customIndexer.GetSearcher())
                            {
                                var waitHandle = new ManualResetEvent(false);

                                void OperationComplete(object sender, IndexOperationEventArgs e)
                                {
                                    //signal that we are done
                                    waitHandle.Set();
                                }

                                //add the handler for optimized since we know it will be optimized last based on the commit count
                                customIndexer.IndexOperationComplete += OperationComplete;

                                //remove the normal indexing error handler
                                //customIndexer.IndexingError -= IndexInitializer.IndexingError;

                                //run in async mode
                                customIndexer.RunAsync = true;

                                //get all nodes
                                var nodes = _contentService.GetPublishedContentByXPath("//*[@isDoc]")
                                            .Root
                                            .Elements()
                                            .ToList();

                                Func <int, XElement> getNode = (index) =>
                                {
                                    // clone it
                                    return(new XElement(nodes[index]));
                                };

                                // we know there are 20 documents available, this is important for the getNode call
                                var idQueue = new ConcurrentQueue <int>(Enumerable.Range(1, 20));

                                var searchCountPerThread = Convert.ToInt32(searchCount / searchThreadCount);
                                var indexCountPerThread  = Convert.ToInt32(indexCount / indexThreadCount);

                                //spawn a bunch of threads to perform some reading
                                var tasks = new List <Task>();

                                Action <ISearcher> doSearch = (s) =>
                                {
                                    try
                                    {
                                        for (var counter = 0; counter < searchCountPerThread; counter++)
                                        {
                                            //get next id and put it to the back of the list
                                            int docId;
                                            if (idQueue.TryDequeue(out docId))
                                            {
                                                idQueue.Enqueue(docId);
                                                var r = s.CreateQuery().Id(docId.ToString()).Execute();
                                                Console.WriteLine("searching thread: {0}, id: {1}, found: {2}", Thread.CurrentThread.ManagedThreadId, docId, r.Count());
                                                Thread.Sleep(searchThreadWait);
                                            }
                                        }
                                    }
                                    catch (Exception ex)
                                    {
                                        Console.WriteLine("Search ERROR!! {0}", ex);
                                        throw;
                                    }
                                };

                                Action <IIndex> doIndex = (ind) =>
                                {
                                    try
                                    {
                                        //reindex a nodes a bunch of times
                                        for (var i = 0; i < indexCountPerThread; i++)
                                        {
                                            //get next id and put it to the back of the list
                                            int docId;
                                            if (idQueue.TryDequeue(out docId))
                                            {
                                                idQueue.Enqueue(docId);

                                                var node = getNode(docId - 1);
                                                node.Attribute("id").Value = docId.ToString(CultureInfo.InvariantCulture);
                                                Console.WriteLine("Indexing {0}", docId);
                                                ind.IndexItems(new[] { node.ConvertToValueSet(IndexTypes.Content) });
                                                Thread.Sleep(indexThreadWait);
                                            }
                                        }
                                    }
                                    catch (Exception ex)
                                    {
                                        Console.WriteLine("Index ERROR!! {0}", ex);
                                        throw;
                                    }
                                };

                                //indexing threads
                                for (var i = 0; i < indexThreadCount; i++)
                                {
                                    var indexer = customIndexer;
                                    tasks.Add(Task.Run(() => doIndex(indexer)));
                                }

                                //searching threads
                                for (var i = 0; i < searchThreadCount; i++)
                                {
                                    var searcher = customSearcher;
                                    tasks.Add(Task.Run(() => doSearch(searcher)));
                                }

                                try
                                {
                                    Task.WaitAll(tasks.ToArray());
                                }
                                catch (AggregateException e)
                                {
                                    var sb = new StringBuilder();
                                    sb.Append(e.Message + ": ");
                                    foreach (var v in e.InnerExceptions)
                                    {
                                        sb.Append(v.Message + "; ");
                                    }
                                    Assert.Fail(sb.ToString());
                                }

                                var results = customSearcher.CreateQuery().All().Execute();
                                Assert.AreEqual(20, results.Count());

                                //reset the async mode and remove event handler
                                //customIndexer.IndexingError += IndexInitializer.IndexingError;
                                //customIndexer.RunAsync = false;

                                //wait until we are done
                                waitHandle.WaitOne();

                                writer.WaitForMerges();
                                writer.Dispose(true);

                                results = customSearcher.CreateQuery().All().Execute();
                                Assert.AreEqual(20, results.Count());
                            }
            }
            finally
            {
                if (temp != null)
                {
                    try
                    {
                        temp.Delete(true);
                    }
                    catch (Exception ex)
                    {
                        Console.WriteLine("Could not delete temp folder {0}", ex);
                    }
                }
            }
        }