directory-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From akaras...@apache.org
Subject svn commit: r649759 - in /directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src: main/java/org/apache/directory/server/xdbm/search/impl/ test/java/org/apache/directory/server/xdbm/search/impl/
Date Sat, 19 Apr 2008 05:08:12 GMT
Author: akarasulu
Date: Fri Apr 18 22:08:12 2008
New Revision: 649759

URL: http://svn.apache.org/viewvc?rev=649759&view=rev
Log:
100% code coverage on SubstringEvaluator and SubstringCursor

Modified:
    directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/main/java/org/apache/directory/server/xdbm/search/impl/SubstringCursor.java
    directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/main/java/org/apache/directory/server/xdbm/search/impl/SubstringEvaluator.java
    directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/test/java/org/apache/directory/server/xdbm/search/impl/SubstringTest.java

Modified: directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/main/java/org/apache/directory/server/xdbm/search/impl/SubstringCursor.java
URL: http://svn.apache.org/viewvc/directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/main/java/org/apache/directory/server/xdbm/search/impl/SubstringCursor.java?rev=649759&r1=649758&r2=649759&view=diff
==============================================================================
--- directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/main/java/org/apache/directory/server/xdbm/search/impl/SubstringCursor.java
(original)
+++ directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/main/java/org/apache/directory/server/xdbm/search/impl/SubstringCursor.java
Fri Apr 18 22:08:12 2008
@@ -23,11 +23,9 @@
 import org.apache.directory.server.core.cursor.AbstractCursor;
 import org.apache.directory.server.core.cursor.Cursor;
 import org.apache.directory.server.core.cursor.InvalidCursorPositionException;
-import org.apache.directory.server.core.partition.impl.btree.IndexAssertion;
 import org.apache.directory.server.xdbm.IndexEntry;
 import org.apache.directory.server.xdbm.Store;
-import org.apache.directory.server.xdbm.Index;
-import org.apache.directory.shared.ldap.filter.SubstringNode;
+import org.apache.directory.server.xdbm.ForwardIndexEntry;
 
 import javax.naming.directory.Attributes;
 
@@ -42,52 +40,24 @@
 {
     private static final String UNSUPPORTED_MSG =
         "SubstringCursors may not be ordered and do not support positioning by element.";
-    private Cursor<IndexEntry<String,Attributes>> wrapped;
-    private IndexAssertion<String,Attributes> indexAssertion;
+    private final boolean hasIndex;
+    private final Cursor<IndexEntry<String,Attributes>> wrapped;
+    private final SubstringEvaluator evaluator;
+    private final ForwardIndexEntry<String,Attributes> indexEntry =
+        new ForwardIndexEntry<String,Attributes>();
     private boolean available = false;
 
 
     public SubstringCursor( Store<Attributes> db,
                             final SubstringEvaluator substringEvaluator ) throws Exception
     {
-        SubstringNode node = substringEvaluator.getExpression();
+        evaluator = substringEvaluator;
+        hasIndex = db.hasUserIndexOn( evaluator.getExpression().getAttribute() );
 
-        if ( db.hasUserIndexOn( node.getAttribute() ) )
+        if ( hasIndex )
         {
-            /*
-             * Get the user index and return an index enumeration using the the
-             * compiled regular expression.  Try to constrain even further if
-             * an initial term is available in the substring expression.
-             */
             //noinspection unchecked
-            Index<String,Attributes> idx = db.getUserIndex( node.getAttribute() );
-
-            if ( null == node.getInitial() )
-            {
-                wrapped = idx.forwardCursor();
-            }
-            else
-            {
-                wrapped = idx.forwardCursor( node.getInitial() );
-            }
-
-            /*
-             * The Cursor used is over the index for this attribute so the
-             * values are already normalized.  The value of the IndexEntry is
-             * the value of the attribute (not the ndn as below when we do not
-             * have an Index for the attribute).  All we have to do is see if
-             * the value of the IndexEntry is matched by the filter and
-             * return the result.  We reuse the regex Pattern already compiled
-             * for the substringEvaluator instead of recompiling for this
-             * Cursor.
-             */
-            indexAssertion = new IndexAssertion<String,Attributes>()
-            {
-                public boolean assertCandidate( final IndexEntry<String,Attributes>
entry ) throws Exception
-                {
-                    return substringEvaluator.getPattern().matcher( entry.getValue() ).matches();
-                }
-            };
+            wrapped = db.getUserIndex( evaluator.getExpression().getAttribute() ).forwardCursor();
         }
         else
         {
@@ -103,21 +73,13 @@
              * the node's attribute.
              */
             wrapped = db.getNdnIndex().forwardCursor();
-
-            indexAssertion = new IndexAssertion<String,Attributes>()
-            {
-                public boolean assertCandidate( final IndexEntry<String,Attributes>
entry ) throws Exception
-                {
-                    return substringEvaluator.evaluate( entry );
-                }
-            };
         }
     }
 
 
     public boolean available()
     {
-        return false;
+        return available;
     }
 
 
@@ -135,15 +97,55 @@
 
     public void beforeFirst() throws Exception
     {
-        wrapped.beforeFirst();
+        if ( evaluator.getExpression().getInitial() != null && hasIndex )
+        {
+            ForwardIndexEntry<String,Attributes> indexEntry = new ForwardIndexEntry<String,Attributes>();
+            indexEntry.setValue( evaluator.getExpression().getInitial() );
+            wrapped.before( indexEntry );
+        }
+        else
+        {
+            wrapped.beforeFirst();
+        }
+
+        clear();
+    }
+
+
+    private void clear()
+    {
         available = false;
+        indexEntry.setObject( null );
+        indexEntry.setId( null );
+        indexEntry.setValue( null );
     }
 
 
     public void afterLast() throws Exception
     {
-        wrapped.afterLast();
-        available = false;
+        if ( evaluator.getExpression().getInitial() != null && hasIndex )
+        {
+            ForwardIndexEntry<String,Attributes> indexEntry = new ForwardIndexEntry<String,Attributes>();
+            indexEntry.setValue( evaluator.getExpression().getInitial() );
+            wrapped.after( indexEntry );
+
+            /*
+             * The above operation advances us past the first index entry
+             * matching the initial value.  Lexographically there may still be
+             * entries with values ahead that match and are greater than the
+             * initial string. So we advance until we cannot match anymore.
+             */
+            while ( evaluateCandidate( indexEntry ) && wrapped.next() )
+            {
+                // do nothing but advance
+            }
+        }
+        else
+        {
+            wrapped.afterLast();
+        }
+
+        clear();
     }
 
 
@@ -154,6 +156,19 @@
     }
 
 
+    private boolean evaluateCandidate( IndexEntry<String,Attributes> indexEntry ) throws
Exception
+    {
+        if ( hasIndex )
+        {
+            return evaluator.getPattern().matcher( indexEntry.getValue() ).matches();
+        }
+        else
+        {
+            return evaluator.evaluate( indexEntry );
+        }
+    }
+
+
     public boolean last() throws Exception
     {
         afterLast();
@@ -166,13 +181,18 @@
         while ( wrapped.previous() )
         {
             IndexEntry<String,Attributes> entry = wrapped.get();
-            if ( indexAssertion.assertCandidate( entry ) )
+            if ( evaluateCandidate( entry ) )
             {
-                return available = true;
+                available = true;
+                this.indexEntry.setId( entry.getId() );
+                this.indexEntry.setValue( entry.getValue() );
+                this.indexEntry.setObject( entry.getObject() );
+                return true;
             }
         }
 
-        return available = false;
+        clear();
+        return false;
     }
 
 
@@ -181,13 +201,18 @@
         while ( wrapped.next() )
         {
             IndexEntry<String,Attributes> entry = wrapped.get();
-            if ( indexAssertion.assertCandidate( entry ) )
+            if ( evaluateCandidate( entry ) )
             {
-                return available = true;
+                available = true;
+                this.indexEntry.setId( entry.getId() );
+                this.indexEntry.setValue( entry.getValue() );
+                this.indexEntry.setObject( entry.getObject() );
+                return true;
             }
         }
 
-        return available = false;
+        clear();
+        return false;
     }
 
 
@@ -195,7 +220,7 @@
     {
         if ( available )
         {
-            return wrapped.get();
+            return indexEntry;
         }
 
         throw new InvalidCursorPositionException( "Cursor has yet to be positioned." );
@@ -212,5 +237,6 @@
     {
         super.close();
         wrapped.close();
+        clear();
     }
 }

Modified: directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/main/java/org/apache/directory/server/xdbm/search/impl/SubstringEvaluator.java
URL: http://svn.apache.org/viewvc/directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/main/java/org/apache/directory/server/xdbm/search/impl/SubstringEvaluator.java?rev=649759&r1=649758&r2=649759&view=diff
==============================================================================
--- directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/main/java/org/apache/directory/server/xdbm/search/impl/SubstringEvaluator.java
(original)
+++ directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/main/java/org/apache/directory/server/xdbm/search/impl/SubstringEvaluator.java
Fri Apr 18 22:08:12 2008
@@ -36,6 +36,7 @@
 import org.apache.directory.shared.ldap.schema.AttributeType;
 import org.apache.directory.shared.ldap.schema.MatchingRule;
 import org.apache.directory.shared.ldap.schema.Normalizer;
+import org.apache.directory.shared.ldap.schema.NoOpNormalizer;
 import org.apache.directory.shared.ldap.util.AttributeUtils;
 
 
@@ -90,7 +91,15 @@
             rule = type.getEquality();
         }
 
-        normalizer = rule.getNormalizer();
+        if ( rule != null )
+        {
+            normalizer = rule.getNormalizer();
+        }
+        else
+        {
+            normalizer = new NoOpNormalizer();
+        }
+        
         // compile the regular expression to search for a matching attribute
         regex = node.getRegex( normalizer );
 
@@ -114,7 +123,8 @@
 
         if ( idx == null )
         {
-            return evaluateWithoutIndex( indexEntry );
+            //noinspection unchecked
+            return evaluateWithoutIndex( ( IndexEntry<String,Attributes> ) indexEntry
);
         }
         else
         {
@@ -163,7 +173,7 @@
     }
 
 
-    private boolean evaluateWithoutIndex( IndexEntry<?,Attributes> indexEntry ) throws
Exception
+    private boolean evaluateWithoutIndex( IndexEntry<String,Attributes> indexEntry
) throws Exception
     {
         Attributes entry = indexEntry.getObject();
 
@@ -174,19 +184,11 @@
             indexEntry.setObject( entry );
         }
 
-        // Of course, if the entry does not contains any attributes
-        // (very unlikely !!!), get out of here
-        // TODO Can this simply happens ??? Full test coverage will show it
-        if ( entry == null )
-        {
-            return false;
-        }
-
         // get the attribute
         Attribute attr = AttributeUtils.getAttribute( entry, type );
 
         // if the attribute does not exist just return false
-        if ( attr != null)
+        if ( attr != null )
         {
 
             /*
@@ -204,6 +206,9 @@
                 // Once match is found cleanup and return true
                 if ( regex.matcher( value ).matches() )
                 {
+                    // before returning we set the normalized value
+                    indexEntry.setValue( value );
+                    
                     values.close();
                     return true;
                 }

Modified: directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/test/java/org/apache/directory/server/xdbm/search/impl/SubstringTest.java
URL: http://svn.apache.org/viewvc/directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/test/java/org/apache/directory/server/xdbm/search/impl/SubstringTest.java?rev=649759&r1=649758&r2=649759&view=diff
==============================================================================
--- directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/test/java/org/apache/directory/server/xdbm/search/impl/SubstringTest.java
(original)
+++ directory/sandbox/akarasulu/bigbang/apacheds/xdbm-search/src/test/java/org/apache/directory/server/xdbm/search/impl/SubstringTest.java
Fri Apr 18 22:08:12 2008
@@ -37,7 +37,6 @@
 import org.junit.Before;
 import org.junit.After;
 import org.junit.Test;
-import org.junit.Ignore;
 import static org.junit.Assert.assertEquals;
 import static org.junit.Assert.assertTrue;
 import static org.junit.Assert.assertFalse;
@@ -128,8 +127,7 @@
 
 
     @Test
-    @Ignore ( "Broken Test" )
-    public void testIndexedAttributes() throws Exception
+    public void testIndexedCnStartsWithJ() throws Exception
     {
         SubstringNode node = new SubstringNode( SchemaConstants.CN_AT_OID, "j", null );
         SubstringEvaluator evaluator = new SubstringEvaluator( node, store, registries );
@@ -139,29 +137,536 @@
         assertTrue( cursor.isElementReused() );
 
         cursor.beforeFirst();
+
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 8, ( long ) cursor.get().getId() );
+        assertEquals( "jack daniels", cursor.get().getValue() );
+
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 5, ( long ) cursor.get().getId() );
+        assertEquals( "johnny walker", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 11, ( long ) cursor.get().getId() );
+        assertEquals( "johnny walker", cursor.get().getValue() );
+
+        assertFalse( cursor.next() );
+        assertFalse( cursor.available() );
+
+        assertFalse( cursor.isClosed() );
+        cursor.close();
+        assertTrue( cursor.isClosed() );
+
+        // ---------- test first ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.first();
+
+        assertTrue( cursor.available() );
+        assertEquals( 8, ( long ) cursor.get().getId() );
+        assertEquals( "jack daniels", cursor.get().getValue() );
+
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
         assertTrue( cursor.next() );
         assertTrue( cursor.available() );
         assertEquals( 5, ( long ) cursor.get().getId() );
+        assertEquals( "johnny walker", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 11, ( long ) cursor.get().getId() );
+        assertEquals( "johnny walker", cursor.get().getValue() );
+
+        assertFalse( cursor.next() );
+        assertFalse( cursor.available() );
+
+
+        // ---------- test afterLast ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.afterLast();
+        assertFalse( cursor.available() );
+
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 11, ( long ) cursor.get().getId() );
+        assertEquals( "johnny walker", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 5, ( long ) cursor.get().getId() );
+        assertEquals( "johnny walker", cursor.get().getValue() );
+
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 8, ( long ) cursor.get().getId() );
+        assertEquals( "jack daniels", cursor.get().getValue() );
+
+        assertFalse( cursor.previous() );
+        assertFalse( cursor.available() );
+
+        // ---------- test last ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.last();
+        assertTrue( cursor.available() );
+
+        assertEquals( 11, ( long ) cursor.get().getId() );
+        assertEquals( "johnny walker", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 5, ( long ) cursor.get().getId() );
+        assertEquals( "johnny walker", cursor.get().getValue() );
+
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 8, ( long ) cursor.get().getId() );
+        assertEquals( "jack daniels", cursor.get().getValue() );
+
+        assertFalse( cursor.previous() );
+        assertFalse( cursor.available() );
+    }
+
+
+    @Test
+    public void testIndexedCnStartsWithJim() throws Exception
+    {
+        SubstringNode node = new SubstringNode( SchemaConstants.CN_AT_OID, "jim", null );
+        SubstringEvaluator evaluator = new SubstringEvaluator( node, store, registries );
+        SubstringCursor cursor = new SubstringCursor( store, evaluator );
+
+        assertEquals( node, evaluator.getExpression() );
+        assertTrue( cursor.isElementReused() );
+
+        cursor.beforeFirst();
+
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
         assertTrue( cursor.next() );
         assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
+        assertFalse( cursor.next() );
+        assertFalse( cursor.available() );
+
+        // ---------- test first ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.first();
+
+        assertTrue( cursor.available() );
         assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
         assertTrue( cursor.next() );
         assertTrue( cursor.available() );
-        assertEquals( 7, ( long ) cursor.get().getId() );
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
         assertFalse( cursor.next() );
         assertFalse( cursor.available() );
+
+
+        // ---------- test afterLast ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.afterLast();
+        assertFalse( cursor.available() );
+
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
+        assertFalse( cursor.previous() );
+        assertFalse( cursor.available() );
+
+        // ---------- test last ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.last();
+        assertTrue( cursor.available() );
+
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
+        assertFalse( cursor.previous() );
+        assertFalse( cursor.available() );
+    }
+
+
+    @Test
+    public void testIndexedCnEndsWithBean() throws Exception
+    {
+        SubstringNode node = new SubstringNode( SchemaConstants.CN_AT_OID, null, "bean" );
+        SubstringEvaluator evaluator = new SubstringEvaluator( node, store, registries );
+        SubstringCursor cursor = new SubstringCursor( store, evaluator );
+
+        assertEquals( node, evaluator.getExpression() );
+        assertTrue( cursor.isElementReused() );
+
+        cursor.beforeFirst();
+
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
+        assertFalse( cursor.next() );
+        assertFalse( cursor.available() );
+
+        // ---------- test first ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.first();
+
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
+        assertFalse( cursor.next() );
+        assertFalse( cursor.available() );
+
+
+        // ---------- test afterLast ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.afterLast();
+        assertFalse( cursor.available() );
+
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
+        assertFalse( cursor.previous() );
+        assertFalse( cursor.available() );
+
+        // ---------- test last ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.last();
+        assertTrue( cursor.available() );
+
+        assertEquals( 10, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 9, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "jim bean", cursor.get().getValue() );
+
+        assertFalse( cursor.previous() );
+        assertFalse( cursor.available() );
+    }
+
+
+    @Test
+    public void testNonIndexedSnStartsWithB() throws Exception
+    {
+        SubstringNode node = new SubstringNode( SchemaConstants.SN_AT_OID, "b", null );
+        SubstringEvaluator evaluator = new SubstringEvaluator( node, store, registries );
+        SubstringCursor cursor = new SubstringCursor( store, evaluator );
+
+        assertEquals( node, evaluator.getExpression() );
+        assertTrue( cursor.isElementReused() );
+
+        cursor.beforeFirst();
+
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "bean", cursor.get().getValue() );
+
+        assertFalse( cursor.next() );
+        assertFalse( cursor.available() );
+        cursor.close();
+
+        // ---------- test first ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.first();
+
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "bean", cursor.get().getValue() );
+
+        assertFalse( cursor.next() );
+        assertFalse( cursor.available() );
+
+
+        // ---------- test afterLast ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.afterLast();
+        assertFalse( cursor.available() );
+
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "bean", cursor.get().getValue() );
+
+        assertFalse( cursor.previous() );
+        assertFalse( cursor.available() );
+
+        // ---------- test last ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.last();
+        assertTrue( cursor.available() );
+
+        assertTrue( cursor.available() );
+        assertEquals( 6, ( long ) cursor.get().getId() );
+        assertEquals( "bean", cursor.get().getValue() );
+
+        assertFalse( cursor.previous() );
+        assertFalse( cursor.available() );
+    }
+
+
+    @Test
+    public void testIndexedSnEndsWithEr() throws Exception
+    {
+        SubstringNode node = new SubstringNode( SchemaConstants.SN_AT_OID, null, "er" );
+        SubstringEvaluator evaluator = new SubstringEvaluator( node, store, registries );
+        SubstringCursor cursor = new SubstringCursor( store, evaluator );
+
+        assertEquals( node, evaluator.getExpression() );
+        assertTrue( cursor.isElementReused() );
+
+        cursor.beforeFirst();
+
+        assertTrue( cursor.next() );
+        assertTrue( cursor.available() );
+        assertEquals( 5, ( long ) cursor.get().getId() );
+        assertEquals( "walker", cursor.get().getValue() );
+
+        assertFalse( cursor.next() );
+        assertFalse( cursor.available() );
+
+        // ---------- test first ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.first();
+
+        assertTrue( cursor.available() );
+        assertEquals( 5, ( long ) cursor.get().getId() );
+        assertEquals( "walker", cursor.get().getValue() );
+
+        assertFalse( cursor.next() );
+        assertFalse( cursor.available() );
+
+
+        // ---------- test afterLast ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.afterLast();
+        assertFalse( cursor.available() );
+
+        assertTrue( cursor.previous() );
+        assertTrue( cursor.available() );
+        assertEquals( 5, ( long ) cursor.get().getId() );
+        assertEquals( "walker", cursor.get().getValue() );
+
+        assertFalse( cursor.previous() );
+        assertFalse( cursor.available() );
+
+        // ---------- test last ----------
+
+        cursor = new SubstringCursor( store, evaluator );
+        cursor.last();
+        assertTrue( cursor.available() );
+
+        assertTrue( cursor.available() );
+        assertEquals( 5L, ( long ) cursor.get().getId() );
+        assertEquals( "walker", cursor.get().getValue() );
+
+        assertFalse( cursor.previous() );
+        assertFalse( cursor.available() );
     }
 
 
     @Test
     public void testNonIndexedAttributes() throws Exception
     {
+        SubstringNode node = new SubstringNode( SchemaConstants.SN_AT_OID, "walk", null );
+        SubstringEvaluator evaluator = new SubstringEvaluator( node, store, registries );
+        ForwardIndexEntry<String,Attributes> indexEntry = new ForwardIndexEntry<String,Attributes>();
+        indexEntry.setId( 5L );
+        assertTrue( evaluator.evaluate( indexEntry ) );
+        indexEntry.setId( 3L );
+        indexEntry.setObject( null );
+        assertFalse( evaluator.evaluate( indexEntry ) );
+        indexEntry.setId( 6L );
+        indexEntry.setObject( null );
+        assertFalse( evaluator.evaluate( indexEntry ) );
+
+        node = new SubstringNode( SchemaConstants.SN_AT_OID, "wa", null );
+        evaluator = new SubstringEvaluator( node, store, registries );
+        indexEntry = new ForwardIndexEntry<String,Attributes>();
+        indexEntry.setId( 5L );
+        indexEntry.setObject( store.lookup( 5L ) );
+        assertTrue( evaluator.evaluate( indexEntry ) );
+
+        node = new SubstringNode( SchemaConstants.SEARCHGUIDE_AT_OID, "j", null );
+        evaluator = new SubstringEvaluator( node, store, registries );
+        indexEntry = new ForwardIndexEntry<String,Attributes>();
+        indexEntry.setId( 6L );
+        indexEntry.setObject( store.lookup( 6L ) );
+        assertFalse( evaluator.evaluate( indexEntry ) );
+
+        node = new SubstringNode( SchemaConstants.ST_AT_OID, "j", null );
+        evaluator = new SubstringEvaluator( node, store, registries );
+        indexEntry = new ForwardIndexEntry<String,Attributes>();
+        indexEntry.setId( 6L );
+        indexEntry.setObject( store.lookup( 6L ) );
+        assertFalse( evaluator.evaluate( indexEntry ) );
+
+        node = new SubstringNode( SchemaConstants.NAME_AT_OID, "j", null );
+        evaluator = new SubstringEvaluator( node, store, registries );
+        indexEntry = new ForwardIndexEntry<String,Attributes>();
+        indexEntry.setId( 6L );
+        indexEntry.setObject( store.lookup( 6L ) );
+        assertTrue( evaluator.evaluate( indexEntry ) );
+
+        node = new SubstringNode( SchemaConstants.NAME_AT_OID, "s", null );
+        evaluator = new SubstringEvaluator( node, store, registries );
+        indexEntry = new ForwardIndexEntry<String,Attributes>();
+        indexEntry.setId( 6L );
+        indexEntry.setObject( store.lookup( 6L ) );
+        assertTrue( evaluator.evaluate( indexEntry ) );
     }
 
 
     @Test
     public void testEvaluatorIndexed() throws Exception
     {
+        SubstringNode node = new SubstringNode( SchemaConstants.CN_AT_OID, "jim", null );
+        SubstringEvaluator evaluator = new SubstringEvaluator( node, store, registries );
+        ForwardIndexEntry<String,Attributes> indexEntry = new ForwardIndexEntry<String,Attributes>();
+        indexEntry.setId( 6L );
+        assertTrue( evaluator.evaluate( indexEntry ) );
+        indexEntry.setId( 3L );
+        indexEntry.setObject( null );
+        assertFalse( evaluator.evaluate( indexEntry ) );
+
+        node = new SubstringNode( SchemaConstants.CN_AT_OID, "j", null );
+        evaluator = new SubstringEvaluator( node, store, registries );
+        indexEntry = new ForwardIndexEntry<String,Attributes>();
+        indexEntry.setId( 6L );
+        indexEntry.setObject( store.lookup( 6L ) );
+        assertTrue( evaluator.evaluate( indexEntry ) );
+
+        node = new SubstringNode( SchemaConstants.CN_AT_OID, "s", null );
+        evaluator = new SubstringEvaluator( node, store, registries );
+        indexEntry = new ForwardIndexEntry<String,Attributes>();
+        indexEntry.setId( 6L );
+        indexEntry.setObject( store.lookup( 6L ) );
+        assertFalse( evaluator.evaluate( indexEntry ) );
     }
 
 
@@ -174,7 +679,7 @@
     @Test ( expected = InvalidCursorPositionException.class )
     public void testInvalidCursorPositionException() throws Exception
     {
-        SubstringNode node = new SubstringNode( SchemaConstants.SN_AT_OID, "j", null );
+        SubstringNode node = new SubstringNode( SchemaConstants.SN_AT_OID, "b", null );
         SubstringEvaluator evaluator = new SubstringEvaluator( node, store, registries );
         SubstringCursor cursor = new SubstringCursor( store, evaluator );
         cursor.get();



Mime
View raw message