go to  ForumEasy.com   
LdapPro  
 
 
   Home  |  MyForum  |  FAQ  |  Archive    You are not logged in. [Login] or [Register]  
Forum Home » LDAP Operations & Controls » LDAP Search Paged Results Control
Email To Friend  |   Set Alert To This Topic Rewarding Points Availabe: 0 (What's this) New Topic  |   Post Reply
Author Topic: LDAP Search Paged Results Control
SteveHB
member
offline   
 
posts: 113
joined: 05/31/2006
from: Mountain View, CA
  posted on: 09/06/2006 12:47:48 PM    Edit  |   Quote  |   Report 
LDAP Search Paged Results Control
This control may be useful when the LDAP client has limited resources and may not be able to process the entire result set from a given LDAP query, or when the LDAP client is connected over a low-bandwidth connection.

The structure of this control is as follows:
pagedResultsControl ::= SEQUENCE {
        controlType     1.2.840.113556.1.4.319,
        criticality     BOOLEAN DEFAULT FALSE,
        controlValue    searchControlValue
}

The searchControlValue is an OCTET STRING wrapping the BER-encoded version of the following SEQUENCE:
realSearchControlValue ::= SEQUENCE {
        size            INTEGER (0..maxInt),
                                -- requested page size from client
                                -- result set size estimate from server
        cookie          OCTET STRING
}

 Profile | Reply Points Earned: 0
SteveHB
member
offline   
 
posts: 113
joined: 05/31/2006
from: Mountain View, CA
  posted on: 09/06/2006 12:57:01 PM    Edit  |   Quote  |   Report 
LDAP Search Paged Results Control JNDI Client
The following example shows how a client performs Paged Results Control to interact with server.

/**
 * 
 * PagedResultsControlJndiClient.java
 * Sample code to demostrate how Paged Results Control works.
 * 
 */
 
import javax.naming.*;
import javax.naming.directory.*;
import javax.naming.ldap.*;

import java.util.Hashtable;

public class PagedResultsControlJndiClient 
{
	
  static final String  PAGED_RESULT_CONTROL_OID = "1.2.840.113556.1.4.319";
    
  public static void main(String[] args)
  {
    Hashtable env = new Hashtable();
        
    env.put(Context.INITIAL_CONTEXT_FACTORY, 
                    "com.sun.jndi.ldap.LdapCtxFactory");
        
    // Note: Active Directory Server supports Paged Results Control 
    //       SunOne does not supports Paged Results Control but it supports 
    //       Virtual List View Control instead.
    env.put(Context.PROVIDER_URL, "ldap://myAD.mydomain.com:389");
    env.put(Context.SECURITY_AUTHENTICATION, "simple");
    env.put(Context.SECURITY_PRINCIPAL, "administrator@mydomain.com");
    env.put(Context.SECURITY_CREDENTIALS, "mypassword");
        
    try{
    	
      /* Open an LDAP connection for the provided principal and credentials */
      LdapContext ctx = new InitialLdapContext(env, null);
      System.out.println("Initial binding done!");
            
      /* Query the server to see if the paged result control is supported */ 
      if(!isPagedResultControlSupported(ctx)){
         System.out.println("The server does not support Paged Results Control.");
         System.exit(1);
      }

      /* Activate paged results */
      int pageSize = 5;
      byte[] cookie = null;
      int total;
	        
      ctx.setRequestControls(
              new Control[]{new PagedResultsControl(pageSize, Control.CRITICAL)});
      System.out.println("Paged control set!");

      int count = 0;
      while(true){
        count++;
        System.err.println("Search loop count = " + count);
                    
        SearchControls ctls = new SearchControls();
        ctls.setSearchScope(SearchControls.ONELEVEL_SCOPE);
        ctls.setCountLimit(0);
        // Perform the search
        NamingEnumeration results = ctx.search("dc=mydomain,dc=com", 
                                               "(objectclass=*)", ctls);
	            
        try{
          // Iterate over a batch of search results
          while (results != null && results.hasMore()) {
              // Display an entry
              SearchResult entry = (SearchResult)results.next();
              System.out.println("entryDN=" + entry.getName());
          }
        }catch(Exception pe){
          System.out.println(pe.toString());  // Patial Result Exception
        }
	            
        // Examine the paged results control response 
        Control[] controls = ctx.getResponseControls();
        if(controls!=null){
          for(int k = 0; k<controls.length; k++){
            if(controls[k] instanceof PagedResultsResponseControl){
              PagedResultsResponseControl prrc = 
                       (PagedResultsResponseControl)controls[k];
              total = prrc.getResultSize();
              cookie = prrc.getCookie();
            }else{
              // Handle other response controls (if any)
            }
          }
        }
	
        if(cookie==null)
          break;
	            
         // Re-activate paged results
         ctx.setRequestControls(new Control[]{
             new PagedResultsControl(pageSize, cookie, Control.CRITICAL)});
       }
	
       // Close the LDAP association
       ctx.close();
     }catch (Exception e){
       e.printStackTrace();
     }
  }

  /**
   * Is paged result control supported?
   *
   * Query the rootDSE object to find out if the paged result control
   * is supported.
   */
  static boolean isPagedResultControlSupported(LdapContext ctx) 
				throws NamingException
  {
    SearchControls ctl = new SearchControls();
    ctl.setReturningAttributes(new String[]{"supportedControl"});
    ctl.setSearchScope(SearchControls.OBJECT_SCOPE);

    /* search for the rootDSE object */
    NamingEnumeration results = ctx.search("", "(objectClass=*)", ctl);

    while(results.hasMore()){
      SearchResult entry = (SearchResult)results.next();
      NamingEnumeration attrs = entry.getAttributes().getAll();
      while (attrs.hasMore()){
      	Attribute attr = (Attribute)attrs.next();
       	NamingEnumeration vals = attr.getAll();
        while (vals.hasMore()){
        String value = (String) vals.next();
        if(value.equals(PAGED_RESULT_CONTROL_OID))
           return true;
        }
      }
    }
    return false;
  }

}



The above code has been tested against Active Directory 2000 and 2003.

 Profile | Reply Points Earned: 0
SteveHB
member
offline   
 
posts: 113
joined: 05/31/2006
from: Mountain View, CA
  posted on: 09/06/2006 01:14:14 PM    Edit  |   Quote  |   Report 
OperationNotSupportedException
If you run the above client against LDAP servers which do not support Paged Results Control, most likely you are going to get error message similar like this.

javax.naming.OperationNotSupportedException from SunOne Directory Server:

javax.naming.OperationNotSupportedException: [LDAP: error code 12 - Unavailable Critical Extension];
remaining name 'dc=mydomain,dc=com'
at com.sun.jndi.ldap.LdapCtx.mapErrorCode(LdapCtx.java:3045)
at com.sun.jndi.ldap.LdapCtx.processReturnCode(LdapCtx.java:2931)
at com.sun.jndi.ldap.LdapCtx.processReturnCode(LdapCtx.java:2737)
at com.sun.jndi.ldap.LdapCtx.searchAux(LdapCtx.java:1808)
at com.sun.jndi.ldap.LdapCtx.c_search(LdapCtx.java:1731)
at com.sun.jndi.toolkit.ctx.ComponentDirContext.p_search(ComponentDirContext.java:368)
at com.sun.jndi.toolkit.ctx.PartialCompositeDirContext.search(PartialCompositeDirContext.java:338)
at com.sun.jndi.toolkit.ctx.PartialCompositeDirContext.search(PartialCompositeDirContext.java:321)
at javax.naming.directory.InitialDirContext.search(InitialDirContext.java:248)


 Profile | Reply Points Earned: 0
SteveHB
member
offline   
 
posts: 113
joined: 05/31/2006
from: Mountain View, CA
  posted on: 09/07/2006 07:48:58 PM    Edit  |   Quote  |   Report 
How does client discard unwanted results in process?
A sequence of paged search requests is abandoned by the client:
  • sending a search request containing a pagedResultsControl with the size set to zero (pageSize=0).
  • sending an LDAP Abandon operation to abandon one paged search request in progress, but this is discouraged.
  • walking away without informing server, definitely this is strongly discouraged.

  •  Profile | Reply Points Earned: 0
    SteveHB
    member
    offline   
     
    posts: 113
    joined: 05/31/2006
    from: Mountain View, CA
      posted on: 09/11/2007 09:31:06 PM    Edit  |   Quote  |   Report 
    What happens if pageSize > MaxPageSize ?
    Take AD for example, its MaxPageSize = 1000 by default, which means each search cannot return results more than 1000. The problem is that you might have no idea of the value of MaxPageSize for a given LDAP server and you might accidentally set pageSize > MaxPageSize, e.g. 1500 > 1000.

    AD will automatically trim the 1500 to 1000 and return only 1000 results each page. That's OK and doesn't hurts anyone.



     Profile | Reply Points Earned: 0
    SteveHB
    member
    offline   
     
    posts: 113
    joined: 05/31/2006
    from: Mountain View, CA
      posted on: 09/11/2007 09:43:21 PM    Edit  |   Quote  |   Report 
    What happens if pageSize > sizeLimit ?
    For a given search, there is always a bound size limit, either 0 or something. For the value of 0 which means no limit, it's OK for any value of pageSize. For sizeLimit !=0, if pageSize <= sizeLimit, it's still OK, but if pageSize > sizeLimit, you would get something like this:

    javax.naming.SizeLimitExceededException: [LDAP: error code 4 - Sizelimit Exceeded]; remaining name 'dc=mydomain,dc=com'

     Profile | Reply Points Earned: 0
    SteveHB
    member
    offline   
     
    posts: 113
    joined: 05/31/2006
    from: Mountain View, CA
      posted on: 03/11/2008 06:59:49 PM    Edit  |   Quote  |   Report 
    What happens if pageSize < sizeLimit ?

    'sizeLimit' will be ignored by nature.

    Search Paged Results Control is per operation rather than connection. When you associate the Search Paged Results Control with a search, you expect the number of results returned is governed by 'pageSize' -- the 'sizeLimit' is therefore useless for this search.

     Profile | Reply Points Earned: 0
    SteveHB
    member
    offline   
     
    posts: 113
    joined: 05/31/2006
    from: Mountain View, CA
      posted on: 01/23/2012 01:08:36 PM    Edit  |   Quote  |   Report 
    What happens if client sends request again and again?
    A client may have any number of outstanding search requests pending,
       any of which may have used the pagedResultsControl.  A server
       implementation which requires a limit on the number of outstanding
       paged search requests from a given client MAY either return
       unwillingToPerform when the client attempts to create a new paged
       search request, or age out an older result set.  If the server
       implementation ages out an older paged search request, it SHOULD
       return "unwilling to perform" if the client attempts to resume the
       paged search that was aged out.
    


    In order to serve the PagedResultsControl, the serve may have to prepare and hold the whole result set on the server side for each client associated a cookie. If a client open too many requests and leave them open without consuming the results, this will be a burden on server and might choke the server. In that sense, the server can defense itself by aged out the previous requests for the specific client.



     Profile | Reply Points Earned: 0
    Naziya
    member
    offline   
     
    posts: 3
    joined: 01/26/2012
    from: Bangalore, Karnataka
    India
      posted on: 01/26/2012 04:21:09 AM    Edit  |   Quote  |   Report 
    Thanks. It worked fine serving the purpose and saved my time. :-)
     Profile | Reply Points Earned: 0
    Naziya
    member
    offline   
     
    posts: 3
    joined: 01/26/2012
    from: Bangalore, Karnataka
    India
      posted on: 01/26/2012 04:21:57 AM    Edit  |   Quote  |   Report 
    SizelimitException
    Thanks. It worked fine serving the purpose and saved my time. :-)
     Profile | Reply Points Earned: 0
    Naziya
    member
    offline   
     
    posts: 3
    joined: 01/26/2012
    from: Bangalore, Karnataka
    India
      posted on: 01/26/2012 04:28:13 AM    Edit  |   Quote  |   Report 
    SizeLimitException
    Thanks. Worked fine for me serving the purpose and saved my time :-)
     Profile | Reply Points Earned: 0
    ziaur22311
    member
    offline   
     
    posts: 4
    joined: 02/23/2012
    from: Lausanne, Switzerland
    Switzerland
      posted on: 02/24/2012 01:13:57 AM    Edit  |   Quote  |   Report 
    I get a no controls were sent from te server.
    The code loooks good, but how to proceed when LDAP servers do not support Paged Results Control.
    Rather how to fetch large records from (>1000) from LDAP.

    Also how does one know, what type of LDAP server, we are communicating with.

    I do not get the PagedResultsResponseControl object from the ccontext, any help would be appreciated.
     Profile | Reply Points Earned: 0
    ziaur22311
    member
    offline   
     
    posts: 4
    joined: 02/23/2012
    from: Lausanne, Switzerland
    Switzerland
      posted on: 02/24/2012 01:52:00 AM    Edit  |   Quote  |   Report 
    LimitExceededException
    When i set the sdeaxr scope to SearchControls.SUBTREE_SCOPE...

    I get the following exception..

    javax.naming.LimitExceededException: [LDAP: error code 11 - Administrative Limit Exceeded]; remaining name 'ou=larcAccs,ou=WI,ou=larcAppls,ou=AURA,ou=Credit Suisse,o=CREDIT SUISSE GROUP'
    at com.sun.jndi.ldap.LdapCtx.mapErrorCode(LdapCtx.java:3126)
    at com.sun.jndi.ldap.LdapCtx.processReturnCode(LdapCtx.java:2987)
    at com.sun.jndi.ldap.LdapCtx.processReturnCode(LdapCtx.java:2794)
    at com.sun.jndi.ldap.LdapNamingEnumeration.getNextBatch(LdapNamingEnumeration.java:129)
    at com.sun.jndi.ldap.LdapNamingEnumeration.hasMoreImpl(LdapNamingEnumeration.java:198)
    at com.sun.jndi.ldap.LdapNamingEnumeration.hasMore(LdapNamingEnumeration.java:171)
    at PagedSearch.main(PagedSearch.java:76)
     Profile | Reply Points Earned: 0
    ziaur22311
    member
    offline   
     
    posts: 4
    joined: 02/23/2012
    from: Lausanne, Switzerland
    Switzerland
      posted on: 02/24/2012 01:52:13 AM    Edit  |   Quote  |   Report 
    LimitExceededException
    When i set the sdeaxr scope to SearchControls.SUBTREE_SCOPE...

    I get the following exception..

    javax.naming.LimitExceededException: [LDAP: error code 11 - Administrative Limit Exceeded]; remaining name 'ou=larcAccs,ou=WI,ou=larcAppls,ou=AURA,ou=Credit Suisse,o=CREDIT SUISSE GROUP'
    at com.sun.jndi.ldap.LdapCtx.mapErrorCode(LdapCtx.java:3126)
    at com.sun.jndi.ldap.LdapCtx.processReturnCode(LdapCtx.java:2987)
    at com.sun.jndi.ldap.LdapCtx.processReturnCode(LdapCtx.java:2794)
    at com.sun.jndi.ldap.LdapNamingEnumeration.getNextBatch(LdapNamingEnumeration.java:129)
    at com.sun.jndi.ldap.LdapNamingEnumeration.hasMoreImpl(LdapNamingEnumeration.java:198)
    at com.sun.jndi.ldap.LdapNamingEnumeration.hasMore(LdapNamingEnumeration.java:171)
    at PagedSearch.main(PagedSearch.java:76)
     Profile | Reply Points Earned: 0
    ziaur22311
    member
    offline   
     
    posts: 4
    joined: 02/23/2012
    from: Lausanne, Switzerland
    Switzerland
      posted on: 02/24/2012 01:52:24 AM    Edit  |   Quote  |   Report 
    LimitExceededException
    When i set the sdeaxr scope to SearchControls.SUBTREE_SCOPE...

    I get the following exception..

    javax.naming.LimitExceededException: [LDAP: error code 11 - Administrative Limit Exceeded]; remaining name 'ou=larcAccs,ou=WI,ou=larcAppls,ou=AURA,ou=Credit Suisse,o=CREDIT SUISSE GROUP'
    at com.sun.jndi.ldap.LdapCtx.mapErrorCode(LdapCtx.java:3126)
    at com.sun.jndi.ldap.LdapCtx.processReturnCode(LdapCtx.java:2987)
    at com.sun.jndi.ldap.LdapCtx.processReturnCode(LdapCtx.java:2794)
    at com.sun.jndi.ldap.LdapNamingEnumeration.getNextBatch(LdapNamingEnumeration.java:129)
    at com.sun.jndi.ldap.LdapNamingEnumeration.hasMoreImpl(LdapNamingEnumeration.java:198)
    at com.sun.jndi.ldap.LdapNamingEnumeration.hasMore(LdapNamingEnumeration.java:171)
    at PagedSearch.main(PagedSearch.java:76)
     Profile | Reply Points Earned: 0
    krithiga
    member
    offline   
     
    posts:
    joined: 05/03/2012
    from: Karanataka
    India
      posted on: 05/03/2012 03:09:38 AM    Edit  |   Quote  |   Report 
    LDAP paged result control
    I have a requirement the i need to fetch all the records from AD even if it is more than 1000 entries. I tried using PagedResult control (from net) it works fine for filter which has less than 1000 entries. But if the filter fetches more than 1000 (that is needed)

    (JAVA)
    result is namingEnumeration

    results.hasmore loop returns false and not going in to the loop.

    What would be the reason it is failing?

    Very urgent.Please help me in this regard.

    Using the same code as above.
     Profile | Reply Points Earned: 0
    krithiga
    member
    offline   
     
    posts:
    joined: 05/03/2012
    from: Karanataka
    India
      posted on: 05/03/2012 03:10:00 AM    Edit  |   Quote  |   Report 
    LDAP paged result control
    I have a requirement the i need to fetch all the records from AD even if it is more than 1000 entries. I tried using PagedResult control (from net) it works fine for filter which has less than 1000 entries. But if the filter fetches more than 1000 (that is needed)

    (JAVA)
    result is namingEnumeration

    results.hasmore loop returns false and not going in to the loop.

    What would be the reason it is failing?

    Very urgent.Please help me in this regard.

    Using the same code as above.
     Profile | Reply Points Earned: 0
    krithiga
    member
    offline   
     
    posts:
    joined: 05/03/2012
    from: Karanataka
    India
      posted on: 05/03/2012 03:10:13 AM    Edit  |   Quote  |   Report 
    LDAP paged result control
    I have a requirement the i need to fetch all the records from AD even if it is more than 1000 entries. I tried using PagedResult control (from net) it works fine for filter which has less than 1000 entries. But if the filter fetches more than 1000 (that is needed)

    (JAVA)
    result is namingEnumeration

    results.hasmore loop returns false and not going in to the loop.

    What would be the reason it is failing?

    Very urgent.Please help me in this regard.

    Using the same code as above.
     Profile | Reply Points Earned: 0

     
    Powered by ForumEasy © 2003-2005, All Rights Reserved. | Privacy Policy | Terms of Use
     
    Get your own forum today. It's easy and free.