Creating user on local machine is really slow when adding to groups
<p>I have the following code that takes a username and a password and then creates the user on the machine and adds them to two specific groups. When I get to the group part it is really slow and I have no idea why. My last run according to my logs file says that adding the user to the Users group took 7 minutes, but the IIS_IUSRS was super fast.</p>

<p>below is my initial code that calls the methods that do the real work. I have tried using a task to help speed up the process of checking for groups, but it still runs super slow.</p>

<pre><code>public void Apply(Section.User.User user, Action&lt;string&gt; status)
    {
        #region Sanity Checks

        if (user == null)
        {
            throw new ArgumentNullException("user");
        }

        if (status == null)
        {
            throw new ArgumentNullException("status");
        }
        #endregion
        _logger.Debug(string.Format("Starting to apply the user with name {0}", user.UserName));
        status(string.Format("Applying User {0} to the system.", user.UserName));

        using (PrincipalContext pc = new PrincipalContext(ContextType.Machine))
        {

            UserPrincipal userPrincipal = UserPrincipal.FindByIdentity(pc, user.UserName);
            try
            {
                _logger.Debug("Checking if user already exists");
                if (userPrincipal == null)
                {
                    userPrincipal = CreateNewUser(user, pc);
                }

                _logger.Debug("Setting user password and applying to the system.");
                userPrincipal.SetPassword(user.UserPassword);
                userPrincipal.Save();

                Task&lt;PrincipalSearchResult&lt;Principal&gt;&gt; groups =
                    Task&lt;PrincipalSearchResult&lt;Principal&gt;&gt;.Factory.StartNew(userPrincipal.GetGroups);

                _logger.Debug("Adding user to the groups.");
                AddUserToGroups(pc, userPrincipal, groups, user.UserType.Equals(UserType.WorkerProcess.ToString()) ? "Administrators" : "Users", "IIS_IUSRS");
                AddCurrentUser(user);
            }
            finally
            {
                if (userPrincipal != null)
                {
                    userPrincipal.Dispose();
                }
            }


        }

    }
</code></pre>

<p>This is my private method I use to create the user if it doesn't exist.</p>

<pre><code>private UserPrincipal CreateNewUser(Section.User.User user, PrincipalContext principal)
    {
        _logger.Debug("User did not exist creating now.");
        UserPrincipal newUser = new UserPrincipal(principal)
            {
                Name = user.UserName,
                Description = user.UserDescription,
                UserCannotChangePassword = false,
                PasswordNeverExpires = true,
                PasswordNotRequired = false
            };
        _logger.Debug("User created.");
        return newUser;
    }
</code></pre>

<p>Below is the logic for the groups. I have made a comment above the offending code that I get hung on whenever I walk through with the debugger. Also the debug log entry is always the last one I get before the hang as well.</p>

<pre><code>private void AddUserToGroups(PrincipalContext principal, UserPrincipal user, Task&lt;PrincipalSearchResult&lt;Principal&gt;&gt; userGroups, params string[] groups)
    {
        groups.AsParallel().ForAll(s =&gt;
            {
                using (GroupPrincipal gp = GroupPrincipal.FindByIdentity(principal, s))
                {
                    _logger.Debug(string.Format("Checking if user is alread in the group."));
                    if (gp != null &amp;&amp; !userGroups.Result.Contains(gp))
                    {
                        _logger.Debug(string.Format("The user was not a member of {0} adding them now.", gp.Name));
                        //This is the point that the 7 minute hang starts
                        gp.Members.Add(user);
                        gp.Save();

                        _logger.Debug(string.Format("User added to {0}.", gp.Name));
                    }
                }
            });
    }
</code></pre>

<p>Any help with this would be greatly appreciated as this project is expected to release in October, but I can't release with a 7 minute hang when creating a user.</p>
