`
zhao_weigang
  • 浏览: 17022 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

Ldap 分页问题

 
阅读更多

很多文章中都有相关分页操作,以下是我使用分页操作时出现的问题,以及如何解决。

使用VirtualListViewControl分页时,还存在点问题(就是查询第一页和第二页的时候,有几条数据是重复的,希望有高手可以指点下。)

源码在附件中有。附件中是好几种分页的实现。但都不是很完美。希望有高手分享下。

package com.zhao.edu;

import javax.naming.NamingEnumeration;
import javax.naming.directory.Attribute;
import javax.naming.directory.Attributes;
import javax.naming.directory.SearchControls;
import javax.naming.directory.SearchResult;
import javax.naming.ldap.Control;
import javax.naming.ldap.InitialLdapContext;
import javax.naming.ldap.SortControl;

public class LdapSearch {
	
	private static final String ldapHost = "ldap://192.168.32.128:389";
	private static final String loginDN = "cn=Administrator,cn=Users,dc=zhao,dc=edu,dc=com";
	private static final String password = "zhaowg";
	
	public static void main(String[] args) throws Exception{
		InitialLdapContext ctx = LdapConnection.getLdapContext(ldapHost,loginDN,password);
		try {
			
			int pageNum = 30;
			int pageSize = 500;
			SearchControls constraints = new SearchControls();
			constraints.setSearchScope(SearchControls.SUBTREE_SCOPE);
            constraints.setCountLimit(0);
            constraints.setTimeLimit(5000);
            constraints.setDerefLinkFlag(false);
            String[] attrIDs = { "sAMAccountName" ,"distingguishedName"};
            constraints.setReturningAttributes(attrIDs);
            VirtualListViewControl vctl = new VirtualListViewControl(
                    (pageNum-1)*pageSize+1, 0, 0,pageSize-1, Control.CRITICAL);
            SortControl sctl = new SortControl(
                    new String[] { "sAMAccountName" },Control.CRITICAL);
            ctx.setRequestControls(new Control[] { sctl, vctl });
            
            String baseDN="dc=zhao,dc=edu,dc=com";
            String filter="objectClass=*";
            
            NamingEnumeration<SearchResult> results = ctx.search(
                    baseDN,filter, constraints);
                int total = 0;
                while (results != null && results.hasMore()) {
                    total++;
                    SearchResult result = results.nextElement();
                    String value = result.getName();
                    //System.out.print(total + " 节点DN: " + value);
                    Attributes attrs = result.getAttributes();
                    Attribute ocAttr= attrs.get("sAMAccountName");
                    for(int i=0;ocAttr!=null && i<ocAttr.size();i++){
                      System.out.print(" " + ocAttr.get(i) +"\r\n");
                    }
                }
                System.out.println("查询条数:" + total);
		} catch (Exception e) {
			e.printStackTrace();
		} finally {
			LdapConnection.closeLdapContext(ctx);
		}
		
	}
}

 

 

package com.zhao.edu;

import java.util.Hashtable;

import javax.naming.Context;
import javax.naming.NamingException;
import javax.naming.directory.DirContext;
import javax.naming.ldap.InitialLdapContext;

public class LdapConnection {

	/* 服务提供者 */
	private static String CTX_FACTORY = "com.sun.jndi.ldap.LdapCtxFactory";

	/**
	 * 获取上下文
	 * @param url
	 * @param username
	 * @param pwd
	 * @return
	 */
	public static InitialLdapContext  getLdapContext(String url, String username,
			String pwd) {

		Hashtable<String, String> env = new Hashtable<String, String>();
		env.put(Context.INITIAL_CONTEXT_FACTORY, CTX_FACTORY);
		env.put(Context.PROVIDER_URL, url);
		env.put(Context.SECURITY_AUTHENTICATION, "simple");
		env.put(Context.SECURITY_PRINCIPAL, username);
		env.put(Context.SECURITY_CREDENTIALS, pwd);
		DirContext ctx = null;
		try {
			ctx = new InitialLdapContext(env, null);
			System.out.println("认证成功");
		} catch (NamingException e) {
			e.printStackTrace();
			System.out.println("认证失败");
		}
		return (InitialLdapContext) ctx;
	}
	
	/**
	 * 关闭上下文
	 * @param ctx
	 * @throws NamingException
	 */
	public static void closeLdapContext(DirContext ctx) throws NamingException
	{
		if(null!=ctx)
		{
			ctx.close();
			System.out.println("关闭连接"); 
		}
	}
}

 

package com.zhao.edu;

import java.io.IOException;
import javax.naming.directory.InvalidAttributeValueException;
import javax.naming.ldap.*;
import com.sun.jndi.ldap.BasicControl;
import com.sun.jndi.ldap.Ber;
import com.sun.jndi.ldap.BerEncoder;

/**
 * This class implements the LDAPv3 Request Control for virtual-list-view
 * as defined in
 * <a href="http://www.ietf.org/internet-drafts/draft-ietf-ldapext-ldapv3-vlv-09.txt">draft-ietf-ldapext-ldapv3-vlv-09.txt</a>.
 *
 * The control's value has the following ASN.1 definition:
 * <pre>
 *
 *     VirtualListViewRequest ::= SEQUENCE {
 *         beforeCount    INTEGER (0 .. maxInt),
 *         afterCount     INTEGER (0 .. maxInt),
 *         CHOICE {
 *             byoffset [0] SEQUENCE {
 *                 offset          INTEGER (0 .. maxInt),
 *                 contentCount    INTEGER (0 .. maxInt)
 *             }
 *             greaterThanOrEqual [1] AssertionValue
 *         }
 *         contextID     OCTET STRING OPTIONAL
 *     }
 *
 * </pre>
 *
 * This control is always used in conjunction with the server-side sort control
 * (<a href="http://www.ietf.org/rfc/rfc2891.txt">RFC-2891</a>).
 *
 * @see VirtualListViewResponseControl
 * @see SortControl
 * @author Vincent Ryan
 */
final public class VirtualListViewControl extends BasicControl {

    /**
     * The virtual-list-view control's assigned object identifier
     * is 2.16.840.1.113730.3.4.9.
     */
    public static final String OID = "2.16.840.1.113730.3.4.9";

    /** 
     * The number of entries before the target entry in a sublist.
     *
     * @serial
     */
    private int beforeCount;

    /** 
     * The number of entries after the target entry in a sublist.
     *
     * @serial
     */
    private int afterCount;

    /** 
     * An offset into the list.
     *
     * @serial
     */
    private int targetOffset = -1;

    /** 
     * An estimate of the number of entries in the list.
     *
     * @serial
     */
    private int listSize;

    /** 
     * Attribute value used to locate the target entry.
     * This value is compared to values of the attribute specified
     * as the primary sort key.
     *
     * Only String and byte[] values are currently supported.
     *
     * @serial
     */
    private Object targetAttrValue = null;

    /**
     * A server-generated cookie.
     *
	     * @serial
	     */
	    private byte[] cookie = null;
	
	    private static final long serialVersionUID = 7739016048653396131L;
	
	    /**
	     * Constructs a virtual-list-view control.
	     *
	     * Request a view of a portion of the list centered around a given
	     * target entry. The position of the target entry is estimated as a
	     * percentage of the list.
	     *
	     * @param targetPercentage The position of the target entry expressed as a
	     *                       percentage of the list. For example, a value of
	     *                       25 indicates that the target entry is at the
	     *                       25 percent mark in the list.
	     * @param viewSize       The number of entries to be returned in this
	     *                       view of the list.
	     * @param criticality    The control's criticality setting.
	     * @exception        IllegalArgumentException if targetPercentage is
	     *                       outside the range 0-100.
	     * @exception            IOException If a BER encoding error occurs.
	     */
	    public VirtualListViewControl(int targetPercentage, int viewSize,
	    boolean criticality) throws IOException {
	
	    super(OID, criticality, null);
	
	        if ((targetPercentage > 100) ||
	        (targetPercentage < 0) ||
	        (viewSize < 0)) {
	            throw new IllegalArgumentException();
	        }
	
	    targetOffset = targetPercentage;
	    listSize = 100;
	
	    // viewSize includes the target entry
	    if (viewSize > 0) {
	        viewSize -= 1;
	    }
	    beforeCount = afterCount = viewSize / 2;
	
	    // adjust afterCount when viewSize is odd
	    if (viewSize != ((viewSize / 2) * 2)) {
	        afterCount++;
	    }
	    super.value = setEncodedValue();
	    }
	
	    /**
	     * Constructs a virtual-list-view control.
	     *
	     * Request a view of a portion of the list with the specified number of
	     * entries before and after a given target entry. The target entry is
	     * identified by means of an offset into the list.
	     *
	     * @param targetOffset The position of the target entry as an offset
	     *                     into the list.
	     * @param listSize    An estimate of the number of entries in the list.
	     * @param beforeCount  The number of entries to be returned before the
	     *                     target entry.
	     * @param afterCount   The number of entries to be returned after the
	     *                     target entry.
	     * @param criticality  The control's criticality setting.
	     * @exception          IllegalArgumentException if targetOffset, listSize,
	     *                     beforeCount or afterCount are less than zero.
	     * @exception          IOException If a BER encoding error occurs.
	     */
	    public VirtualListViewControl(int targetOffset, int listSize,
	    int beforeCount, int afterCount, boolean criticality)
	    throws IOException {
	
	    super(OID, criticality, null);
	
	    if ((targetOffset <0) || (listSize <0) ||(beforeCount <0) || (afterCount <0)){
	            throw new IllegalArgumentException();
	        }
	    
	    this.targetOffset = targetOffset;
	    this.listSize = listSize;
	    this.beforeCount = beforeCount;
	    this.afterCount = afterCount;
	    super.value = setEncodedValue();
	    }
	
	    /**
	     * Constructs a virtual-list-view critical control.
	     *
	     * Request a view of a portion of the list centered around a given
	     * target entry. The target entry is the first entry that is greater
	     * than or equal to the specified attribute value. The value's 
	     * attribute ID is the primary sort key specified in the server-side
	     * sort control.
	     *
	     * @param targetAttrValue  An attribute value used to locate the target
	     *                         entry. Its attribute ID is that of the primary
	     *                         sort key specified in the server-side sort
	     *                         control.
	     * @param viewSize         The number of entries to be returned in this
	     *                         view of the list.
	     * @param criticality      The control's criticality setting.
	     * @exception          InvalidAttributeValueException if
	     *                         targetAttrValue is neither a String nor a byte[].
	     * @exception              IOException If a BER encoding error occurs.
	     */
	    public VirtualListViewControl(Object targetAttrValue, int viewSize,
	    boolean criticality)
	    throws InvalidAttributeValueException, IOException {
	
	    super(OID, criticality, null);
	
	    if ((targetAttrValue == null) ||
	        (! ((targetAttrValue instanceof String) ||
	            (targetAttrValue instanceof byte[])))) {
	        throw new InvalidAttributeValueException();
	    }
	    this.targetAttrValue = targetAttrValue;
	
	    if (viewSize < 0) {
	        throw new IllegalArgumentException();
	    }
	
	        // viewSize includes the target entry
	        if (viewSize > 0) {
	            viewSize -= 1;
	        }
	    beforeCount = afterCount = viewSize / 2;
	
	    // adjust afterCount when viewSize is odd
	    if (viewSize != ((viewSize / 2) * 2)) {
	        afterCount++;
	    }
	    super.value = setEncodedValue();
	    }
	
	    /**
	     * Constructs a virtual-list-view control.
	     *
	     * Request a view of a portion of the list with the specified number of
	     * entries before and after a given target entry. The target entry is
	     * the first entry that is greater than or equal to the specified
	     * attribute value. The value's attribute ID is the primary sort key
	     * specified in the server-side sort control.
	     *
	     * @param targetAttrValue An attribute value used to locate the target
	     *                        entry. Its attribute ID is that of the primary
	     *                        sort key specified in the server-side sort
	     *                        control.
	     * @param beforeCount     The number of entries to be returned before the
	     *                        target entry.
	     * @param afterCount      The number of entries to be returned after the
	     *                        target entry.
	     * @param criticality     The control's criticality setting.
	     * @exception         InvalidAttributeValueException if
	     *                        targetAttrValue is neither a String nor a byte[].
	     * @exception             IllegalArgumentException if beforeCount or
	     *                        afterCount are less than zero.
	     * @exception             IOException If a BER encoding error occurs.
	     */
	    public VirtualListViewControl(Object targetAttrValue, int beforeCount,
	    int afterCount, boolean criticality)
	    throws InvalidAttributeValueException, IOException {
	
	    super(OID, criticality, null);
	
	    if ((targetAttrValue == null) ||
	        (! ((targetAttrValue instanceof String) ||
	            (targetAttrValue instanceof byte[])))) {
	        throw new InvalidAttributeValueException();
	    }
	
	    if ((beforeCount <0) || (afterCount <0)) {
	        throw new IllegalArgumentException();
	    }
	
	    this.targetAttrValue = targetAttrValue;
	    this.beforeCount = beforeCount;
	    this.afterCount = afterCount;
	    super.value = setEncodedValue();
	    }
	
	    /**
	     * Sets a server-generated cookie in the virtual-list-view request.
	     *
	     * @param contextID A server-generated cookie.
	     * @exception IOException If a BER encoding error occurs.
	     */
	    public void setContextID(byte[] contextID) throws IOException {
	    if (this.cookie != contextID) {
	        this.cookie = contextID;
	        super.value = setEncodedValue(); // re-encode
	    } else {
	        this.cookie = contextID;
	    }
	    }
	
	    /*
	     * Sets the ASN.1 BER encoded value of the virtual-list-view control.
	     * The result is the raw BER bytes including the tag and length of
	     * the control's value. It does not include the controls OID or criticality.
	     *
	     * @return A possibly null byte array representing the ASN.1 BER encoded
	     *         value of the LDAP sort control.
	     * @exception IOException If a BER encoding error occurs.
	     */
	    private byte[] setEncodedValue() throws IOException {
	
	    // build the ASN.1 encoding
	    BerEncoder ber = new BerEncoder(64);
	
	    ber.beginSeq(Ber.ASN_SEQUENCE | Ber.ASN_CONSTRUCTOR);
	
	        ber.encodeInt(beforeCount);
	        ber.encodeInt(afterCount);
	
	        if (targetOffset >= 0) {
	        ber.beginSeq(Ber.ASN_CONTEXT | Ber.ASN_CONSTRUCTOR | 0);
	            ber.encodeInt(targetOffset);
	            ber.encodeInt(listSize);
	        ber.endSeq();
	
	        } else {
	        if (targetAttrValue instanceof String) {
	            ber.encodeString((String)targetAttrValue,
	                     (Ber.ASN_CONTEXT | 1), true);
	        } else { // byte[]
	            ber.encodeOctetString((byte[])targetAttrValue,
	                      (Ber.ASN_CONTEXT | 1));
	        }
	        }
	        if (cookie != null) {
	        ber.encodeOctetString(cookie, Ber.ASN_OCTET_STR);
	        }
	    ber.endSeq();
	
	    return ber.getTrimmedBuf();
	    }
	}

 

 

 

1、搜索结果数据量大于10W或者50W以后,使用VirtualListViewControl.java,会出现异常:

javax.naming.OperationNotSupportedException: [LDAP: error code 12 - 00002040: SvcErr: DSID-031401E7, problem 5010 (UNAVAIL_EXTENSION), data 0

]; remaining name ''

 

解决方案: 设置AD域服务器参数:MaxTempTableSize,默认值为10000。若搜寻结果大于10W,建议设置为15W;若搜索结果大于50w,建议设置100W;若搜索结果大于100W,建议设置200W。(但不知道是否对Ldap服务器其他性能造成影响)

 

2、搜索结果数据量大于10W以上以后,使用PagedResultsControl,出现问题:PageSize设置小于1000.

pageSize设置为1000时,一直在循环获取数据,不会出现异常。若小于1000,则会出现问题。

分享到:
评论

相关推荐

    Spring LDAP API(Spring LDAP 开发文档).CHM

    Spring LDAP。 官网 Spring LDAP API。 Spring LDAP 开发文档。

    基于VB、VC++实现LDAPv3.0源码

    源码均为DEMO实例,包括采用VC++、VB的源码。内容包括了如下四项: Ldap发送请求技术 Ldap分页搜索技术 Ldap检索技术 Ldap异步操作技术

    ldap:GO编程语言的基本LDAP v3功能

    该库实现以下规范: 用于基本操作进行密码修改操作解析专有名称特征: 连接到LDAP服务器(非TLS,TLS,STARTTLS) 绑定到LDAP服务器搜索条目过滤器编译/反编译分页搜索结果修改请求/响应添加请求/响应删除请求/响应...

    XXPageController:分页加载控制器XXPageMenuController。提供了多种不同的分页动态展示效果

    分页菜单加载控制器XXPageMenuController。提供了多种不同的分页动态展示效果。 * 2018年7月6日更新: ================================================== ================= 效果图: 一。 安装安装 可可豆 pod...

    loggrove:Loggrove是对本地、远程日志文件进行 分页阅读、实时阅读、关键词匹配、统计、监控、钉钉告警、Highcharts图表展示 的 Web 平台服务,并包含 用户认证、LDAP认证、操作审计 等基础服务

    Loggrove 是对本地、远程日志文件进行 分页阅读、实时阅读(websocket)、关键词匹配、统计、监控、钉钉告警、Highcharts趋势图展示 的 Web 平台服务,并包含 用户认证、LDAP认证、操作审计 等基础服务。 DEMO 地址...

    IT资产管理系统GLPI 0.84.5.gz

    多种认证系统(Local,LDAP,AD,POP/IMPAP,CAS) 权限系统 分页系统 多语言支持(支持多达14种语言) 搜索模块 显示列表可配置 PDF导出和SLK SQL格式的数据库备份和恢复 下拉列表可配置 更新检查系统 ...

    IT资产管理系统GLPI v0.84.5.zip

    多种认证系统(Local,LDAP,AD,POP/IMPAP,CAS) 权限系统 分页系统 多语言支持(支持多达14种语言) 搜索模块 显示列表可配置 PDF导出和SLK SQL格式的数据库备份和恢复 下拉列表可配置 更新检查系统 ...

    loggrove日志实时查看、轮询、统计、监控工具

    Loggrove是对本地、远程日志文件进行 分页阅读、实时阅读、关键词匹配、统计、监控、钉钉告警、Highcharts图表展示 的 Web 平台服务,并包含 用户认证、LDAP认证、操作审计 等基础服务。

    spring-boot-demo_xkcoding.tar.gz

    ElasticSearch(基本操作和高级查询)、Async(异步任务)、集成Dubbo(采用官方的starter)、MongoDB(文档数据库)、neo4j(图数据库)、docker(容器化)...第三方登录)、LDAP(增删改查)、动态添加/切换数据源、单机限流(AOP +...

    spring boot集成demo大全.zip

    ElasticSearch(`基本操作和高级查询`)、Async(`异步任务`)、集成Dubbo(`采用官方的starter`)、MongoDB(`文档数据库`)、neo4j(`图数据库`)、docker...登录`)、LDAP(`增删改查`)、`动态添加/切换数据源`、单机限流(`AOP +...

    php网络开发完全手册

    15.3.7 结果集的分页 248 15.3.8 用户动态添加记录 249 15.3.9 用户动态更新记录 251 15.3.10 用户动态删除记录 253 15.4 使用PHP获取MySQL数据库的信息 255 15.4.1 获取数据库的信息 255 15.4.2 获取表的信息 256 ...

    ASP3《高级编程》(第一部分)

    第19~23章是关于ASP与BackOffice类应用软件的结合问题,如Microsoft Message Queue Server、Collaborative Data Objects、Microsoft Exchange和Active Directory等等。第24~27章是在企业环境中使用ASP的安全性、性能...

    ASP3《高级编程》(第二部分)

    第19~23章是关于ASP与BackOffice类应用软件的结合问题,如Microsoft Message Queue Server、Collaborative Data Objects、Microsoft Exchange和Active Directory等等。第24~27章是在企业环境中使用ASP的安全性、性能...

    微软Sysinternals Suite工具包 2018.12.18 官方版.zip

    一种 LDAP(轻型目录访问协议)实时监视工具,旨在对 Active Directory 客户端应用程序进行故障排除。AdRestore 恢复已删除的 Server 2003 Active Directory 对象。Autologon 登录过程中跳过密码屏幕。Autoruns ...

    Windows Sysinternals Suite v2019.06.29.zip

    一种 LDAP(轻型目录访问协议)实时监视工具,旨在对 Active Directory 客户端应用程序进行故障排除。 AdRestore 恢复已删除的 Server 2003 Active Directory 对象。 Autologon 登录过程中跳过密码屏幕。 ...

    注册表批量修改权限命令

    AccessChk 能够通过直观的界面和输出快速回答这些问题。 AccessEnum 这一简单但强大的安全工具可以向您显示,谁可以用何种访问权限访问您系统中的目录、文件和注册表项。使用此工具可查找权限漏洞。 AdExplorer ...

    调试开发工具集

    AccessChk 能够通过直观的界面和输出快速回答这些问题。 AccessEnum 这一简单但强大的安全工具可以向您显示,谁可以用何种访问权限访问您系统中的目录、文件和注册表项。使用此工具可查找权限漏洞。 AdExplorer ...

    SysinternalsSuite

    AccessChk 能够通过直观的界面和输出快速回答这些问题。  AccessEnum  这一简单但强大的安全工具可以向您显示,谁可以用何种访问权限访问您系统中的目录、文件和注册表项。使用此工具可查找权限漏洞。  Ad...

    ORACLE9i_优化设计与系统调整

    §7.2 关于创建多个Oracle实例问题 93 §7.3 Oracle系统安装后的优化基础工作 94 §7.3.1 Oracle系统有关目录所有文件的保护 94 §7.3.2 避免新用户使用默认system系统表空间 94 §7.4 Oracle系统所在服务器的独立性...

Global site tag (gtag.js) - Google Analytics