0

Based on code found here, I'm querying an AD group to populate a dropdownlist of associates. The code below takes about 30 seconds to run through, so would just like to make sure I'm using making the best of the code? Ideally I'd like it to run faster, but appreciate around 1500 people is not going to take a few seconds.

            // define AD group to use for populating associate list...
        const string groupName = "Group-Name-X";

        // define array objects...
        var userIdLookup = new SortedList();
        var emailLookup = new SortedList();
        var listContents = new SortedList<string, string>();

        // initialise the AD tools class...
        var adm = new ADMethods();

        // get the members of the specified AD group...
        GroupPrincipal group = adm.GetGroup(groupName);

        // iterate over its members
        foreach (Principal p in group.Members)
        {
            // get the data for the user...
            var groupMember = adm.GetUser(p.SamAccountName);

            // if user account found...
            if (groupMember != null)
            {
                // get the user's mail address...
                string mailAddress = groupMember.EmailAddress ?? p.SamAccountName;

                // if domain extension present ...
                if (mailAddress.Contains("@"))
                {
                    // remove it...
                    mailAddress = mailAddress.Split('@')[0].Trim();
                }

                // create a name starting with surname...
                string associateName = string.Format("{0},", groupMember.Surname);

                // append the first name...
                associateName += string.Format(" {0}", groupMember.GivenName);

                // if the middle name is present...
                if (groupMember.MiddleName != string.Empty)
                {
                    // append it to the string...
                    associateName += string.Format(" {0}", groupMember.MiddleName);
                }

                // get the employee ID...
                string associateNumber = p.SamAccountName;

                // if associate already added...
                if (listContents.ContainsKey(associateName))
                {
                    // skip rest of code for this iteration...
                    continue;
                }

                // add to list that will populate dropdown...
                listContents.Add(associateName, mailAddress);

                // add to lookup collection of ccmail to userID
                userIdLookup.Add(mailAddress, associateNumber);

                // add associate name to list...
                emailLookup.Add(associateNumber, mailAddress);
            }
        }
Martin S
  • 211
  • 1
  • 4
  • 18
  • 1
    There is little you can do about the access time. But if your AD doesn't change very often, you can cache that information. That could save a lot of time – nunespascal Mar 12 '13 at 10:07
  • OK, that's what I guessed but thanks for confirming. I'm caching these lists, and actually create a threaded process when the application launches to do this in the background, but still can't get it to work quick enough to beat the user to where it's needed! Thanks again. – Martin S Mar 12 '13 at 10:19
  • If you are using the `DirectorySearcher` class at all in your ADMethods class, you can use the [`PropertiesToLoad` property](http://msdn.microsoft.com/en-us/library/system.directoryservices.directorysearcher.propertiestoload.aspx) to specify which attributes you want to get back from AD. It sped up some of my queries dramatically. – Josh Darnell Mar 12 '13 at 13:38
  • No, am not using that class at all- this is all based around the Principal class. Thanks anyway. – Martin S Mar 12 '13 at 15:35
  • ad perf issues can arise if you have old crud as members. Ie users that are in non existant domains, external trusted forest that arent there anymore etc – pm100 Mar 21 '13 at 17:49

1 Answers1

0

You may look into performing an attribute scoped query for members on the specific group. As it is currently implemented the slow down is most likely that you have to execute a new search for each member (you'll want to use something like a Stopwatch to verify). With an attribute scoped query you can load all the users in one go and then do your work on them.

I've not tried it with System.DirectoryServices.AccountManagement, but I know you can do it with System.DirectoryServices and System.DirectoryServices.Protocols.

DirectorySearcher example

Alan
  • 456
  • 2
  • 9