title: Active Directory: find details of users in group without mass search
body: <p>OK, working with active directory, my one remaining requirement is to pull back all the users in a given group and get their details - first name, last name, username, email.</p>
  
  <p>Having read up around this I was surprised to discover that there doesn't seem to be a way of doing this in an efficient fashion. I've worked out two ways of getting the results, but both seem absurdly wasteful.</p>
  
  <p>The first is to search members of a group, like this:</p>
  
  <pre><code>        DirectoryEntry searchRoot = new DirectoryEntry("LDAP://" + server, username, password);
          DirectorySearcher search = new DirectorySearcher(searchRoot);
          search.Filter = string.Format("(|(CN={0})(CN={1}))", "Group1", "Group2");
  
          search.PropertiesToLoad.Add("member");
          SearchResultCollection results = search.FindAll();
  </code></pre>
  
  <p>Which brings back a single result containing usernames, and usernames only. You can dissect this into an array of individual usernames, but then to get the details of each user you have to search AD again on a per-name basis.</p>
  
  <p>The other approach is to do this:</p>
  
  <pre><code>   DirectoryEntry searchRoot = new DirectoryEntry("LDAP://" + server, username, password);
      DirectorySearcher search = new DirectorySearcher(searchRoot);
      search.Filter = string.Format("(&amp;(&amp;(objectClass=user)(objectCategory=person))(memberOf=*))");
  
      search.PropertiesToLoad.Add("memberOf");
      search.PropertiesToLoad.Add("name");
      search.PropertiesToLoad.Add("mail");
      search.PropertiesToLoad.Add("displayName");
  
      SearchResultCollection mySearchResultColl = search.FindAll();
  
      foreach (SearchResult result in mySearchResultColl)
      {
          foreach (string prop in result.Properties["memberOf"])
          {
              if (prop.Contains("Group1") || prop.Contain("Group2"))
              {
                 //add user to list
              }
          }
      }
  </code></pre>
  
  <p>Which gets me what I want but involves retrieving every active directory user and then iterating through the collection to find ones that match. That works fine on my little test directory, but I shudder to think how slow it's going to be on a system with thousands of users.</p>
  
  <p>I'm aware you can do what I need using the PrinicpalContext object, but as best I can tell that only works if the code is running in the same domain, which I can't guarantee. I need to be able to query across domains.</p>
  
  <p>Is there a better way of doing this? Or am I just going to have to suck on the performance issues?</p>