Поиск в AD, используя пользователя из другого AD с Java

У меня есть два Active Directory в двух доменах: domain1.xx и domain2.xx У меня есть пользователь, который принадлежит domain1.xx с именем user1. Я могу делать запросы LDAP на domain1, используя user1. Пользователь user1 имеет право на чтение на domain2.xx, и я проверил это с помощью AD Explorer, и это сработало. Проблема в том, что когда я использую Java, он возвращает мне это исключение: ОШИБКА: [LDAP: код ошибки 49 - 80090308: LdapErr: DSID-0C090334, комментарий: ошибка AcceptSecurityContext, данные 525, vece

этот код, соединяющий запросы в domain1 и что он работает:

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","user01@domain1.xx");
        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","user01@domain1.xx");
        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");
            }
        }
    }
}

Может ли кто-нибудь помочь с этим делом. user01@domain1.xx может прочитать все OU в domain2.xx я пробовал это с AD Explorer.

1 ответ

Отправленная вами ошибка аутентификации содержит специальный код, который может быть полезен. В вашем случае код 525 (ошибка AcceptSecurityContext, данные 525). Код 525 означает "Пользователь не найден". Судя по вашему коду, вы повторно используете одного и того же пользователя - user1 @ domain1. Этот пользователь СУЩЕСТВУЕТ только в домене 1. Домен 2 не знает об этом пользователе, поэтому контроллер домена AD отклоняет попытку аутентификации.

Примеры кода, прилагаемые к вопросу, работают с определенными контроллерами домена, а не с глобальными каталогами. Попробуйте сделать следующее:

  • использовать InitialLdapContext вместо InitialDirContext
  • привязка к глобальному каталогу вместо контроллера домена. Для этого используйте URL-адрес ldap: // FQDN: 3268. Пожалуйста, не порт 3268.

Обратите внимание, что порт 3268 не является безопасным.

Надеюсь это поможет.

Другие вопросы по тегам