LDAP绑定与搜索

时间:2013-04-18 07:57:41

标签: java linux ldap unboundid-ldap-sdk

LDAP新手。我计划使用UnboundID Java API通过非常慢的链接检查LDAP服务器中是否存在~5K条目。一个是,我可以使用正确的LDAP搜索选项。或者通过绑定条目的DN来确定条目的存在。 Plz建议,这是快速/最好的方式。

3 个答案:

答案 0 :(得分:6)

您绝对不应该仅仅为了确定条目是否存在而执行绑定。这有几个很好的理由:

  • 符合标准的LDAP服务器应该为您尝试绑定为不存在的用户的情况和您尝试绑定的情况返回“无效凭据”响应使用错误的密码绑定。因此,如果您不知道用户的密码(如果您甚至不知道用户是否存在,这是一个相当不错的选择),那么您不能使用绑定来区分缺少的用户和错误的用户密码

  • 绑定尝试可能会导致写入目标条目,这可能会显着降低性能。如果您尝试使用错误的密码进行绑定,则可以将服务器配置为跟踪失败的身份验证尝试,在某些情况下甚至可能会锁定用户。即使您使用正确的密码绑定,服务器也可能配置为更新条目(例如,记录上次登录时间)。

您可以考虑其他一些选项。它们包括:

  • 正如Terry建议的那样,对请求的属性集为“1.1”的每个条目(这是LDAPConnection.getEntry方法所执行的操作)执行基本级搜索,这意味着没有属性。如果该条目不存在,您将获得“无此对象”结果(这将导致LDAP SDK抛出LDAPException)。如果该条目确实存在,那么您将获得仅包含其DN的搜索结果条目,然后是搜索结果完成响应。

  • 作为使用基本级搜索的替代方法,您可以使用LDAP比较操作。如果您只想知道条目是否存在,那么这比搜索更有效,因为每个条目只有一个响应(比较结果)而不是两个(搜索结果条目和搜索结果完成)。如果条目存在,那么您将根据条目是否与比较断言匹配来获得“比较真实”或“比较假”的响应。如果该条目不存在,那么您将获得一个带有“无此对象”结果的LDAPException。

  • 如果您使用的服务器支持entryDN操作属性(如RFC 5020中所述),那么您可以执行可用于检索多个条目的单个搜索。例如,您可以构造一个类似“(|(entryDN = uid = user.1,dc = example,dc = com)的过滤器(entryDN = uid = user.2,dc = example,dc = com)(entryDN = uid) = user.3,DC =例如,DC = COM)(entryDN = UID = user.4,DC =例如,DC = COM)(entryDN = UID = user.5,DC =例如,DC = COM))”。此示例将用于单个搜索请求,该请求可用于确定这五个条目中的哪一个存在。您可以使用最多五个搜索结果条目响应和一个搜索结果完成响应的单个请求,而不是针对每个条目单独的请求和响应。我绝对不建议使用5000个元素构建OR过滤器,但您仍然可以使用它来显着减少需要执行的搜索请求的数量。

  • 如果您使用的目录没有比您要检查的目录多得多的条目,那么您只需创建一个包含您要查找的DN的集合,执行子树“ (objectClass = *)“搜索,然后从服务器返回的集合中删除每个条目的DN。搜索完成后,集合中剩下的条目将是服务器中不存在的条目。当然,如果您只想检查包含大量条目的服务器中的少数条目,这将是一个非常糟糕的主意。

请注意,在最后两种情况下,您尝试根据是否在一组搜索结果中返回条目来确定条目是否存在,您还将受到访问控制限制的约束。如果您用于绑定到服务器的帐户没有权限查看您尝试检查的所有条目,那么您可能会错误地认为条目不存在只是因为客户端不存在有权看到它。相反,如果您没有权限进行检查,前两种方法可能会返回“访问权限不足”的结果,这也可能导致您无法做出决定。最终,这意味着您应该使用您确定有权查看您需要做出决定的所有条目的帐户。

答案 1 :(得分:2)

如果DN已知,然后客户端正在检查是否存在而未进行身份验证,请检索1.1 OID(无属性),而不是BIND。 BIND通常比搜索慢。例如:

try {
    // Connect to the server
    LDAPConnection ldapConnection = new LDAPConnection(...);
    try {
        for(String dn:listOfDns) {
            Entry entry = ldapConnection.getEntry(dn,"1.1");
        }
    } catch(LDAPException ex) {
        // handle an exception from the search
    } finally {
        ldapConnection.close();
    }
 } catch(LDAPException ex) {
        // handle an exception from the connection attempt
 }

答案 2 :(得分:1)

如果您不需要,请不要搜索。如果您已经知道DN,只需绑定它即可。

然而通常的情况是你知道别的东西,即maildisplayName之类的属性值,所以你必须首先搜索找到具有该属性的条目,然后用它绑定条目的DN。