1

I'm trying to re write a search from System.DirectoryServices to System.DirectoryServices.Protocol

In S.DS I get all the requested attributes back, but in S.DS.P, I don't get the GUID, or the HomePhone...

The rest of it works for one user.

Any Ideas?

public static List<AllAdStudentsCV> GetUsersDistinguishedName( string domain, string distinguishedName )
        {
            try
            {

                NetworkCredential credentials               = new NetworkCredential( ConfigurationManager.AppSettings[ "AD_User" ], ConfigurationManager.AppSettings[ "AD_Pass" ] ); 
                LdapDirectoryIdentifier directoryIdentifier = new LdapDirectoryIdentifier( domain+":389" ); 

                using ( LdapConnection connection           = new LdapConnection( directoryIdentifier, credentials ) )
                {

                    SearchRequest searchRequest = new SearchRequest( );
                    searchRequest.DistinguishedName = distinguishedName;
                    searchRequest.Filter = "(&(objectCategory=person)(objectClass=user)(sn=Afcan))";//"(&(objectClass=user))";
                    searchRequest.Scope = SearchScope.Subtree;
                    searchRequest.Attributes.Add("name");
                    searchRequest.Attributes.Add("sAMAccountName");
                    searchRequest.Attributes.Add("uid");
                    searchRequest.Attributes.Add("telexNumber"); // studId
                    searchRequest.Attributes.Add("HomePhone"); //ctrId
                    searchRequest.SizeLimit = Int32.MaxValue;
                    searchRequest.TimeLimit = new TimeSpan(0, 0, 45, 0);// 45 min - EWB

                    SearchResponse searchResponse = connection.SendRequest(searchRequest) as SearchResponse;

                    if (searchResponse == null) return null;

                    List<AllAdStudentsCV> users = new List<AllAdStudentsCV>();

                    foreach (SearchResultEntry entry in searchResponse.Entries)
                    {
                        AllAdStudentsCV user = new AllAdStudentsCV();

                        user.Active = "Y";
                        user.CenterName = "";
                        user.StudId = GetstringAttributeValue(entry.Attributes, "telexNumber");
                        user.CtrId = GetstringAttributeValue(entry.Attributes, "HomePhone");
                        user.Guid = GetstringAttributeValue(entry.Attributes, "uid");
                        user.Username = GetstringAttributeValue(entry.Attributes, "sAMAccountName");

                        users.Add(user);
                    }

                    return users;
                }
            }
            catch (Exception ex)
            {
                throw;
            }
        }

Also, if I want to fetch EVERY user in AD, so I can synch data with my SQL DB, how do I do that, I Kept getting max size exceeded, errors. I set the size to maxInt32... is there an "ignore size" option?

Thanks,

Eric-

Eric Brown - Cal
  • 14,135
  • 12
  • 58
  • 97
  • Changed 'HomePhone' to 'homePhone' and now i get home phone, but stil no GUID... any idea what it's called here instead of 'uid'? – Eric Brown - Cal Sep 06 '11 at 21:26
  • 1
    To easily find the attribute name (even those that AD doesn't display with regular tools like ldapbrowser), you should try to browse the directory with ADSIEdit (adsiedit.msc on a DC) – sk_ Sep 06 '11 at 21:55
  • @EricBrown-Cal, in your example, would **distinguishedName** be `"user"`? Also, in your Filter, you use `"(sn=Afcan))"`. What is this value? All of LDAP is new and confusing. –  Oct 17 '17 at 20:41

1 Answers1

0

I think that the standard way is to use System.DirectoryServices, not System.DirectoryServices.Protocol. Why do you want to user the later ?

Concerning your second question about the error message "max sized exceeded", it may be because you try to fetch too many entries at once.
Active Directory limits the number of objects returned by query, in order to not overload the directory (the limit is something like 1000 objects). The standard way to fetch all the users is using paging searchs.

The algorithm is like this:

  1. You construct the query that will fetch all the users
  2. You specify a specific control (Paged Result Control) in this query indicating that this is a paged search, with 500 users per page
  3. You launch the query, fetch the first page and parse the first 500 entries in that page
  4. You ask AD for the next page, parse the next 500 entries
  5. Repeat until there are no pages left
sk_
  • 2,105
  • 17
  • 31
  • 1
    S.AD.P is supposed to be alot faster, my first pass on this was implmented with S.DS... but takes 15 min to fetch. We need to fetch all the studetns so I guess paged is the way to go. Found some code samples: – Eric Brown - Cal Sep 06 '11 at 20:48
  • http://dunnry.com/blog/CommentView,guid,1707c3e7-5395-45f4-8882-3a17f291934b.aspx – Eric Brown - Cal Sep 06 '11 at 20:50
  • OK, thanks. S.DS.P seems to allow raw ldap access, as S.DS seems to rely on ADSI and DCOM. I learnt something too today :) 15 minutes to fetch an entire directory is indeed a lot of time. Even with ten of thousands of entries, it should take less than one minute (given you filter the attributes you fetch appropriately). – sk_ Sep 06 '11 at 21:30
  • Did it solve the problem you were facing with AD not sending back all the attributes you requested ? – sk_ Sep 06 '11 at 21:44
  • Yep, The Code I copied was doing case sensitive searches on my end, causing issue with 'HomePhone' and the meaning of uid changed, it's not the GUID any more, I had to ask for 'objectGuid'instead to get the GUID – Eric Brown - Cal Sep 08 '11 at 20:04
  • In the end I wound up rewriting this in S.DS.p for speed. it's went down by a factor of over 20x. 15min to less than 1min (20sec?) – Eric Brown - Cal Feb 07 '13 at 19:58