在AD中使用来自另一个AD的用户在java中搜索
问题描述:
我在两个域中有两个Active Directory:domain1.xx和domain2.xx 我有一个用户属于domain1.xx,名为user1。 我可以使用user1在domain1上执行LDAP查询。 user1在domain2.xx上具有读取权限,并且我已使用AD Explorer对其进行了测试,并且它可以正常工作。 问题是,当我使用Java,它返回我这个例外: 错误:[LDAP:错误代码49 - 80090308:LdapErr:DSID-0C090334,注释:AcceptSecurityContext错误,数据525,vece在AD中使用来自另一个AD的用户在java中搜索
此代码连接查询了域,它的工作原理:
package ad;
import java.util.Enumeration;
import java.util.Hashtable;
import javax.naming.AuthenticationException;
import javax.naming.Context;
import javax.naming.NamingEnumeration;
import javax.naming.directory.Attribute;
import javax.naming.directory.DirContext;
import javax.naming.directory.SearchControls;
import javax.naming.directory.SearchResult;
public class AD {
static DirContext ldapAuthenticate(String password, String userdn) throws Exception {
Hashtable env = new Hashtable();
env.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.ldap.LdapCtxFactory");
//set security credentials, note using simple cleartext authentication
env.put(Context.SECURITY_AUTHENTICATION, "simple");
env.put(Context.SECURITY_PRINCIPAL, userdn);
env.put(Context.SECURITY_CREDENTIALS, password);
//connect to my domain controller
env.put(Context.PROVIDER_URL, "ldap://domain1.xx");
//Create the initial directory context
DirContext ctx = null;
try {
ctx = new javax.naming.directory.InitialDirContext(env);
} catch (AuthenticationException e) {
System.out.println("ERROR: "+e.getMessage());
} catch (Exception e) {
System.out.println("ERROR: "+e.getMessage());
//something went wrong
///handle in some way
}
return ctx;
}
public static void main(String[] args) throws Exception {
DirContext context = ldapAuthenticate("xxxxxx","[email protected]");
String userdn = "dc=domain1,dc=xx";
SearchControls searchCtrls = new SearchControls();
searchCtrls.setSearchScope(SearchControls.SUBTREE_SCOPE);
String[] attributes = {"member"};
searchCtrls.setReturningAttributes(attributes);
//Change the NameOfGroup for the group name you would like to retrieve the members of.
String filter ="objectclass=*";
NamingEnumeration values = context.search(userdn, filter, null);
//Loop through the search results
while (values.hasMoreElements()) {
SearchResult sr = (SearchResult) values.next();
System.out.println(">>>" + sr.getName());
javax.naming.directory.Attributes attrs = sr.getAttributes();
if (null != attrs) {
for (NamingEnumeration ae = attrs.getAll(); ae.hasMoreElements();) {
Attribute atr = (Attribute) ae.next();
String attributeID = atr.getID();
Enumeration vals = atr.getAll();
if (vals.hasMoreElements()) {
String username = (String) vals.nextElement();
System.out.println("Username: " + username);
}
}
} else {
System.out.println("No members for groups found");
}
}
}
}
当我想查询domain2.xx我有例外:
package ad;
import java.util.Enumeration;
import java.util.Hashtable;
import javax.naming.AuthenticationException;
import javax.naming.Context;
import javax.naming.NamingEnumeration;
import javax.naming.directory.Attribute;
import javax.naming.directory.DirContext;
import javax.naming.directory.SearchControls;
import javax.naming.directory.SearchResult;
public class AD {
static DirContext ldapAuthenticate(String password, String userdn) throws Exception {
Hashtable env = new Hashtable();
env.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.ldap.LdapCtxFactory");
//set security credentials, note using simple cleartext authentication
env.put(Context.SECURITY_AUTHENTICATION, "simple");
env.put(Context.SECURITY_PRINCIPAL, userdn);
env.put(Context.SECURITY_CREDENTIALS, password);
//connect to my domain controller
env.put(Context.PROVIDER_URL, "ldap://domain2.xx");
//Create the initial directory context
DirContext ctx = null;
try {
ctx = new javax.naming.directory.InitialDirContext(env);
} catch (AuthenticationException e) {
System.out.println("ERROR: "+e.getMessage());
} catch (Exception e) {
System.out.println("ERROR: "+e.getMessage());
//something went wrong
///handle in some way
}
return ctx;
}
public static void main(String[] args) throws Exception {
DirContext context = ldapAuthenticate("xxxxxx","[email protected]");
String userdn = "dc=domain2,dc=xx";
SearchControls searchCtrls = new SearchControls();
searchCtrls.setSearchScope(SearchControls.SUBTREE_SCOPE);
String[] attributes = {"member"};
searchCtrls.setReturningAttributes(attributes);
//Change the NameOfGroup for the group name you would like to retrieve the members of.
String filter ="objectclass=*";
NamingEnumeration values = context.search(userdn, filter, null);
//Loop through the search results
while (values.hasMoreElements()) {
SearchResult sr = (SearchResult) values.next();
System.out.println(">>>" + sr.getName());
javax.naming.directory.Attributes attrs = sr.getAttributes();
if (null != attrs) {
for (NamingEnumeration ae = attrs.getAll(); ae.hasMoreElements();) {
Attribute atr = (Attribute) ae.next();
String attributeID = atr.getID();
Enumeration vals = atr.getAll();
if (vals.hasMoreElements()) {
String username = (String) vals.nextElement();
System.out.println("Username: " + username);
}
}
} else {
System.out.println("No members for groups found");
}
}
}
}
任何人都可以使用这种情况下帮助。 [email protected]可以读取domain2.xx中的所有OU,我尝试过使用AD Explorer。
答
您发布的身份验证错误包含可能有用的特殊代码。在你的情况下,代码是525(AcceptSecurityContext错误,数据525)。代码525的意思是“用户未找到”。根据您的代码判断您正在重复使用同一用户 - user1 @ domain1。此用户仅在域1中存在。域2不知道此用户,因此AD域控制器拒绝认证尝试。
附加到问题的代码示例针对特定的域控制器运行,而不是全局编录。尽量做到以下几点:
- 使用InitialLdapContext代替InitialDirContext
- 绑定到全局编录,而不是域控制器。为此,请使用URL ldap:// FQDN:3268。请不要端口是3268.
请注意,端口3268是不安全的。
希望这会有所帮助。