如果使用ldapsearch搜索特定LDAP服务器以获取基本级别命名上下文,则搜索工作正常。
$ ldapsearch -h myhealthisp.com -p 10389 -x -s base -b "" namingContexts
# extended LDIF
#
# LDAPv3
# base <> (default) with scope baseObject
# filter: (objectclass=*)
# requesting: namingContexts
#
#
dn:
namingContexts: dc=myhealthisp,dc=com
# search result
search: 2
result: 0 Success
# numResponses: 2
# numEntries: 1`
然而,使用JNDI,我们得到以下响应:
No Results for: myhealthisp.com.
Problem: [LDAP: error code 32 - No Such Object] null
这是我们的代码:
private Attribute getCertFromLdap(SRVRecord srvRec, CertificateInfo certInfo) throws CertLookUpException{
env.put(DirContext.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.ldap.LdapCtxFactory");
sc1 = new SearchControls();
sc1.setSearchScope(SearchControls.ONELEVEL_SCOPE);
try {
env.put(DirContext.PROVIDER_URL, "ldap://" + targetDomain + ":" + srvRec.getPort());
System.out.println("ldap://" + targetDomain + ":" + srvRec.getPort());
DirContext dc = new InitialDirContext(env);
NamingEnumeration directoryNE = null;
System.out.println("Got HERE!");
directoryNE= dc.search("", "objectClass=*", sc1);
System.out.println("SC1 :" + sc1);
while (directoryNE.hasMore()){
SearchResult result1 = (SearchResult) directoryNE.next();
// print DN of entry
System.out.println("Result.getNameInNamespace: " + result1.getName());
Attribute foundMail = findMailAttribute(result1.getNameInNamespace());
if(foundMail != null){
return foundMail;
}
}
dc.close();
} catch (NamingException e) {
System.out.println("No Results for: " + targetDomain + "\nProblem: " + e.getLocalizedMessage() + " " + e.getCause());
} return null;
}
我们能够返回myhealthisp.com的基本目录的唯一方法是将目录名称(dc = myhealthisp,dc = com)硬编码到基本目录搜索过滤器中(请参阅此内容以了解我们的基础代码:http://directory.apache.org/apacheds/manuals/basic-user-guide-1.5.8-SNAPSHOT/html/ch03s03.html#LDAP操作搜索)
当我们的代码搜索onctest.org LDAP服务器时,我们会给每个namingContexts。
以下是onctest.org服务器和myhealthisp.com服务器的Eclipse控制台输出:
ldap://onctest.org.:10389
Got HERE!
SC1 :javax.naming.directory.SearchControls@4c408bfc
Result.getNameInNamespace: ou=config
Result.getNameInNamespace: dc=example,dc=com
Result.getNameInNamespace: ou=system
Search Result: cn=dts556: null:null:{mail=mail: dts556@onctest.org, usercertificate=userCertificate: [B@35e06ba6, objectclass=objectClass: organizationalPerson, person, inetOrgPerson, top, o=o: onctest, sn=sn: Test Case, cn=cn: dts556}
Service Record: _ldap._tcp.onctEst.org. 86400 IN SRV 0 0 10389 onctest.org.
ldap://myhealthisp.com.:10389
Got HERE!
No Results for: myhealthisp.com.
Problem: [LDAP: error code 32 - No Such Object] null
Unable to find certificate at LDAP for: steve.tripp@myhealthisp.com
_ldap._tcp.myhealthisp.com. 3600 IN SRV 0 0 10389 myhealthisp.com.
我们认为以下是造成问题的原因:
答案 0 :(得分:2)
通常,匿名绑定没有权限在根上执行ldap搜索。每个目录都具有匿名绑定的OOTB权限并搜索根目录。在apache DS的情况下,可以通过ldap查询
搜索命名上下文ldapsearch -h localhost -p 10389 -s base -b“”“(objectclass = *)”namingContexts
然而,一级搜索子树搜索,如
ldapsearch -h localhost -p 10389 -s one -b“” - D“uid = admin,ou = system”-w secret“(objectclass = *)”
给出以下结果:这是你在jndi程序中做的: ldap_search:没有这样的对象 ldap_search:附加信息:NO_SUCH_OBJECT:SearchRequest失败 baseDn:'' 过滤器:'(2.5.4.0 = *)' 范围:单级 typesOnly:false 大小限制:没有限制 时间限制:没有限制 Deref别名:从不Deref别名 属性: :null
第一个ldapsearch命令的JNDI代码:
import java.util.Hashtable; import javax.naming.Context; import javax.naming.NamingEnumeration; import javax.naming.NamingException; import javax.naming.directory.Attribute; import javax.naming.directory.Attributes; import javax.naming.directory.DirContext; import javax.naming.directory.InitialDirContext; import javax.naming.directory.SearchControls; import javax.naming.directory.SearchResult; public class SampleLDAPSearch { private Attribute getCertFromLdap() { String targetDomain = "localhost"; String port = "10389"; Hashtable env = new Hashtable(); env.put(DirContext.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.ldap.LdapCtxFactory"); SearchControls sc1 = new SearchControls(); sc1.setSearchScope(SearchControls.OBJECT_SCOPE); sc1.setReturningAttributes(new String[] { "namingContexts" }); try { env.put(DirContext.PROVIDER_URL, "ldap://" + targetDomain + ":" + port); System.out.println("ldap://" + targetDomain + ":" + port); DirContext dc = new InitialDirContext(env); NamingEnumeration directoryNE = null; System.out.println("Got HERE!"); directoryNE = dc.search("", "objectclass=*", sc1); System.out.println("SC1 :" + sc1); while (directoryNE.hasMore()) { SearchResult result1 = (SearchResult) directoryNE.next(); // print DN of entry System.out.println("Result.getNameInNamespace: " + result1.getName()); Attributes attrs = result1.getAttributes(); Attribute attr = attrs.get("namingContexts"); System.out.println(attr); } dc.close(); } catch (NamingException e) { System.out.println("No Results for: " + targetDomain + "\nProblem: " + e.getLocalizedMessage() + " " + e.getCause()); } return null; } public static void main(String[] args) { SampleLDAPSearch sls = new SampleLDAPSearch(); sls.getCertFromLdap(); } }
答案 1 :(得分:0)
当搜索级别不是base
时,不得出现Root DSE。此外,LDAP客户端不得依赖于根DSE中包含的信息,因为这些属性可能受访问控制的保护。来自RFC4512:
These attributes are retrievable, subject to access control and other
restrictions, if a client performs a Search operation [RFC4511] with
an empty baseObject, scope of baseObject, the filter
"(objectClass=*)" [RFC4515], and the attributes field listing the
names of the desired attributes. It is noted that root DSE
attributes are operational and, like other operational attributes,
are not returned in search requests unless requested by name.
将搜索范围更改为base
。更好的是,不要编写依赖于从根DSE检索的对象的代码。