Основная ошибка в AD, когда пользователь находится в группе? - PullRequest
0 голосов
/ 29 мая 2020

У меня есть следующий код, который отлично работает, пока пользователь не входит в определенную группу (groupName)

все значения определены в этой функции или где-то еще и реализованы правильно, значения верны в этой функции:

    public void AddUserToGroup(string userId, string groupName)
    {

        string ss = Password();
        bool bSuccess = false;

        try
        {
            using (PrincipalContext pc = new PrincipalContext(ContextType.Domain, "lhw-nt.local", null, "lhw-nt\\administrator", ss))
            {
                GroupPrincipal group = GroupPrincipal.FindByIdentity(pc, groupName);
                group.Members.Add(pc, IdentityType.UserPrincipalName, userId);                 
                group.Save();

                bSuccess = true;
            }
        } catch (DirectoryServicesCOMException e)
        {
            MessageBox.Show(e.ToString(), "Fehler");
        }

        if(bSuccess)
        {
            MessageBox.Show("Erfolgreich", "Erfolg");
        }

Когда пользователь находится в этой группе, появляется основная ошибка на

group.Members.Add(pc, IdentityType.UserPrincipalName, userId);

и не go прочь даже если пользователь не входит в группу.

Ошибка:

System.DirectoryServices.AccountManagement.No Matching PrincipalException HResult = 0x80131501 Сообщение = Es wurde kein den angegebenen Parametern entsprechender Prinzipal gefunden. Source = System.DirectoryServices.AccountManagement StackTrace: в System.DirectoryServices.AccountManagement.PrincipalCollection.Add (PrincipalContext context, IdentityType identityType, String identityValue)

Я уже пробовал использовать блок try-catch вокруг этого, но ошибка все еще появляется вверх. Что не так?

Ответы [ 2 ]

0 голосов
/ 08 июня 2020

Спасибо за ответ ... Я изучу это через несколько дней, так как у нас сейчас есть другие дела, и я не могу протестировать новый код или созданный нами инструмент. Как только у меня будет информация, я опубликую ее здесь.

0 голосов
/ 29 мая 2020

Эта ошибка не связана с тем, что пользователь уже находится в группе. Это действительно означает, что пользователь не может быть найден.

В этой строке:

group.Members.Add(pc, IdentityType.UserPrincipalName, userId);  

Вы говорите ему сопоставить userId с UserPrincipalName. Соответствует ли значение, которое вы передаете для userId, пользовательскому UserPrincipalName? Он должен выглядеть примерно как username@lhw-nt.local. Если вы передаете только username, вы можете изменить эту строку на IdentityType.SamAccountName.

Как только он может найти пользователя, и пользователь уже находится в группе, он выдаст PrincipalExistsException, который вы можете поймать и даже проигнорировать, если хотите.


Остальная часть этого ответа - просто побочное примечание, которое вы можете игнорировать, если хотите.

Я предпочитаю использовать пространство имен DirectoryServices напрямую, что в любом случае использует пространство имен AccountManagement в фоновом режиме. Это немного больше кода, но у вас гораздо больше контроля над тем, что происходит. Это часто приводит к тому, что код работает быстрее.

Например, вот эквивалентный метод для поиска группы и пользователя по имени и добавления пользователя в группу. Это не вызовет исключения, если пользователь уже является членом группы. Он просто продолжится без звука.

Вы должны обработать случаи, когда группа или пользователь не найдены. Я оставил комментарии в этих местах.

public void AddUserToGroup(string userId, string groupName)
{

    string ss = Password();
    bool bSuccess = false;

    try
    {
        var searchRoot = new DirectoryEntry("LDAP://lhw-nt.local", "lhw-nt\\administrator", ss);

        //Find the group
        var groupSearcher = new DirectorySearcher
        {
            SearchRoot = searchRoot,
            //match group name by either sAMAccountName or cn
            Filter = $"(&(objectClass=group)(|(sAMAccountName={groupName})(cn={groupName})))",
            PropertiesToLoad = { "cn" } //if we omit this, it will load every attribute, which we don't need
        };

        var group = groupSearcher.FindOne()?.GetDirectoryEntry();

        if (group == null)
        {
            //group wasn't found
            return;
        }

        //Find the user
        var userSearcher = new DirectorySearcher
        {
            SearchRoot = searchRoot,
            Filter = $"(userPrincipalName={userId})",
            PropertiesToLoad = { "distinguishedName" }
        };

        var userDn = userSearcher.FindOne()?.Properties["distinguishedName"][0] as string;

        if (userDn == null)
        {
            //user wasn't found
            return;
        }

        //Add the user to the group
        group.Properties["member"].Add(userDn);
        group.CommitChanges();

        bSuccess = true;
    }
    catch (DirectoryServicesCOMException e)
    {
        MessageBox.Show(e.ToString(), "Fehler");
    }

    if (bSuccess)
    {
        MessageBox.Show("Erfolgreich", "Erfolg");
    }
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...