Get user AD groups while logging via LDAP - c#

I'm trying to get group list while authenticating user. And still getting 0 results. I unfortunately have no environment for testing, so I cannot debug this code (only via logger). Have no results and no exceptions.
private LdapResponce IsAuthenticated(string ldap, string usr, string pwd, out List<string> groups)
{
List<string> result = new List<string>();
try
{
using (var searcher = new DirectorySearcher(new DirectoryEntry(ldap, usr, pwd)))
{
searcher.Filter = String.Format("(&(objectCategory=group)(member={0}))", usr);
searcher.SearchScope = SearchScope.Subtree;
searcher.PropertiesToLoad.Add("cn");
_loggingService.Info(searcher.FindAll().Count.ToString());// here i'm getting 0
foreach (SearchResult entry in searcher.FindAll())
{
try
{
if (entry.Properties.Contains("cn"))
result.Add(entry.Properties["cn"][0].ToString());
}
catch (NoMatchingPrincipalException pex)
{
continue;
}
catch (Exception pex)
{
continue;
}
}
}
groups = result;
}
catch (DirectoryServicesCOMException cex)
{
groups = new List<string>();
if (cex.ErrorCode == -2147023570) return LdapResponce.WrongPassword;
return LdapResponce.Error;
}
catch (Exception ex)
{
groups = new List<string>();
return LdapResponce.Error;
}
return LdapResponce.Passed;
}

Add this to the top of your program
using System.DirectoryServices.AccountManagement;
Use this function and pass the username and the group you are looking to see if they are in. if the group has a group nested it will look in the nested group to see if the user is in that group too.
public static Boolean fctADIsInGroup(string LSUserName, string LSGroupName)
{
Boolean LBReturn = false;
// set up domain context
PrincipalContext ctx = new PrincipalContext(ContextType.Domain, "Put your domain name here. Right click on My computer and go to properties to see the domain name");
// find a user
UserPrincipal user = UserPrincipal.FindByIdentity(ctx, LSUserName);
// find the group in question
GroupPrincipal group = GroupPrincipal.FindByIdentity(ctx, LSGroupName);
if (user != null)
{
// check if user is member of that group
if (user.IsMemberOf(group))
{
LBReturn = true;
}
else
{
var LSAllMembers = group.GetMembers(true);
foreach(var LSName in LSAllMembers)
{
string LSGPUserName = LSName.SamAccountName.ToUpper();
if (LSGPUserName == PSUserName.ToUpper())
{
LBReturn = true;
}
}
}
}
return LBReturn;
}

Related

UserSearcher/UserPrinciple: Users have been deleted already

I am trying to use PrincipalSearcher to search for any users with a specific DisplayName and delete them.
If there are no users with a matching DisplayName, the code operates fine. If one is found though, an exception is raised stating:
System.InvalidOperationException: Can't delete an already deleted
object
at System.DirectoryServices.AccountManagement.Principal.CheckDisposedOrDeleted()
at System.DirectoryServices.AccountManagement.Principal.get_Name()}
I have placed a breakpint on user.delete() and can confirm that there is a user present. As soon as the Delete call is made though, the exception is raised.
I can't see where the object has been deleted. Any help would be appreciated.
public string DeleteUsers()
{
using (var principalContext = new PrincipalContext(
ContextType.Machine, null
))
{
using (var userPrincipal = new UserPrincipal(principalContext))
{
// All users will have the same DisplayName
userPrincipal.DisplayName = UserDisplayName;
//
// Search for all users with the above displayName
//
using (var principalSearcher = new PrincipalSearcher(
userPrincipal
))
{
var users = principalSearcher.FindAll();
string userString = "";
// Loop through each of them and delete them
foreach (var user in users)
{
var username = user.Name;
try
{
user.Delete();
}
catch (Exception e)
{
return $"Error: Could not delete user: {username}. " +
$"{e.Message}";
}
if (!String.IsNullOrEmpty(userString))
{
userString += ", ";
}
userString += username;
}
if (String.IsNullOrEmpty(userString))
{
return "No users deleted.";
}
return "Deleted the following users: " + userString;
}
}
}
}

System.DirectoryServices.AccountManagement.NoMatchingPrincipalException: An error occurred while enumerating the groups. The group could not be found

I want to get the Groups of a User from the Active Directory by an User Principal. For this task, I wrote the following static function:
internal static List<ADGroup> GetGroupsByIdentity(UserPrincipal pUserPrincipal)
{
var lResult = new List<ADGroup>();
if (pUserPrincipal != null)
{
PrincipalSearchResult<Principal> lGroups = pUserPrincipal.GetAuthorizationGroups();
// iterate over all groups
foreach (Principal p in lGroups)
{
// make sure to add only group principals
if (p is GroupPrincipal)
{
var lGroupName = "";
var lGroupSid = "";
try
{
lGroupName = p.Name;
lGroupSid = p.Sid.Value;
if (!string.IsNullOrEmpty(lGroupName) && !string.IsNullOrEmpty(lGroupSid) &&
!lResult.Any(x => x.Sid == lGroupSid))
{
lResult.Add(new ADGroup(p));
}
}
catch (Exception e)
{
if (e is PrincipalOperationException || e is NoMatchingPrincipalException)
{
// perhaps the SID could not be resolved
// perhaps the SID does not exist in the AD any more
// ignore and proceed with next
p.Dispose();
continue;
}
else
{
throw;
}
}
finally
{
p.Dispose();
}
}
p.Dispose();
}
}
return lResult;
}
When the user executes this code, he gets an Exception. Here is a part of the stack:
System.DirectoryServices.AccountManagement.NoMatchingPrincipalException:
An error occurred while enumerating the groups. The group could not be found.
at System.DirectoryServices.AccountManagement.AuthZSet.get_CurrentAsPrincipal()
at System.DirectoryServices.AccountManagement.FindResultEnumerator`1.get_Current()
at xxx.xxxxxxxxx.Mvc.CustomSetup.ADHandler.GetGroupsByIdentity(UserPrincipal pUserPrincipal) // the function above
at ...
Where is the problem and how can I solve it?
It seems like the method GetAuthorizationGroups() have a few limitations. This is an old Exception that have existed since 2009. And Microsoft won't fix it because "there is a reasonable workaround". https://connect.microsoft.com/VisualStudio/feedback/details/522539/clr-forum-error-calling-principal-getauthorizationgroups-in-winxp-sp3
I got this error when using Principal.IsMemberOf(). I searched if a user existed in a custom list of groups. If a group didn't exist in the Domain, it threw this
System.DirectryServices.AccountManagement.NoMatchingPrincipalException
https://msdn.microsoft.com/en-us/library/system.directoryservices.accountmanagement.nomatchingprincipalexception(v=vs.110).aspx
Error example 1 using .IsMemberOf()
List<string> groups = Constants.ADGroups(); // List of AD groups to test against
var context = new PrincipalContext(
ContextType.Domain,
"Domain");
var userPrincipal = UserPrincipal.FindByIdentity(
context,
IdentityType.SamAccountName,
httpContext.User.Identity.Name);
// Verify that the user is in the given AD group (if any)
foreach (var group in groups)
if (userPrincipal.IsMemberOf(context, IdentityType.Name, group))
return true;
Error example 2 using .GetAuthorizationGroups():
var context = new PrincipalContext(ContextType.Domain,"Domain");
var userPrincipal = UserPrincipal.FindByIdentity(
context,
IdentityType.SamAccountName,
httpContext.User.Identity.Name);
if (userPrincipal != null)
{
var principalGroups = userPrincipal.GetAuthorizationGroups();
foreach (var principalGroup in principalGroups)
{
foreach (var group in groups)
{
if (String.Equals(
principalGroup.Name,
group,
StringComparison.CurrentCultureIgnoreCase))
{
return true;
}
}
}
}
Solution 1: Proposed workaround is to iterate over AD Groups:
GetAuthorizationGroups() is throwing exception
PrincipalSearchResult<Principal> groups = user.GetAuthorizationGroups();
var iterGroup = groups.GetEnumerator();
using (iterGroup)
{
while (iterGroup.MoveNext())
{
try
{
Principal p = iterGroup.Current;
Console.WriteLine(p.Name);
}
catch (NoMatchingPrincipalException pex)
{
continue;
}
}
}
Solution 2: What I instead ended up using (MVC app using Windows Authentication):
This is a lighter way to check auth, iterating over a large company's AD can be slow...
var wi = HttpContext.Current.User.Identity as WindowsIdentity;
if (wi != null)
{
var wp = new WindowsPrincipal(wi);
List<string> groups = Constants.ADGroups(); // List of AD groups to test against
foreach (var #group in groups)
{
Debug.WriteLine($"Searching for {#group}");
if (wp.IsInRole(#group))
{
return true;
}
}
}

What info do I need to connect to Active Directory in C#?

I need to connect to a clients AD server to display information for all users. They've given me the following:
fqdn, netbios name and a domain controller. Is this enough to connect?
using (var context = new PrincipalContext(ContextType.Domain, "",))
using (var searcher = new PrincipalSearcher(new UserPrincipal(context)))
{
foreach (var result in searcher.FindAll())
{
DirectoryEntry de = result.GetUnderlyingObject() as DirectoryEntry;
}
}
Thanks!
I think Ryan was showing you the old way to do it. From your code it looks like you are using the newer classes.
// create a principal searcher for running a search operation
using (PrincipalSearcher pS = new PrincipalSearcher(uParams))
{
// assign the query filter property for the principal object you created
// you can also pass the user principal in the PrincipalSearcher constructor
pS.QueryFilter = uParams;
// run the query
using (PrincipalSearchResult<Principal> results = pS.FindAll())
{
foreach (Principal item in results)
{
UserPrincipal u = item as UserPrincipal;
list.Add(new MyCustomClass(u.UserPrincipalName)
{
Cn = u.Name,
Email = u.EmailAddress,
EmployeeId = u.EmployeeId,
NameFirst = u.GivenName,
NameLast = u.Surname,
ObjectSid = u.Sid.ToString(),
DistinguishedName = u.DistinguishedName,
SamAccount = u.SamAccountName
});
}
}
}
Note that the AD still imposes sometihng like a 1500 item limit on your queries so you will likely need to send your DirectoryEntry top to something like this:
/// <summary>
/// group member enumeration, simple and fast for large AD groups
/// </summary>
/// <param name="deGroup"></param>
/// <returns>list if distinguished names</returns>
public static List<string> GetMemberList(DirectoryEntry deGroup)
{
List<string> list = new List<string>();
DirectoryEntry entry = deGroup;
uint rangeStep = 1000;
uint rangeLow = 0;
uint rangeHigh = rangeLow + (rangeStep - 1);
bool lastQuery = false;
bool quitLoop = false;
do
{
string attributeWithRange;
if (!lastQuery)
{
attributeWithRange = String.Format("member;range={0}-{1}", rangeLow, rangeHigh);
}
else
{
attributeWithRange = String.Format("member;range={0}-*", rangeLow);
}
using (DirectorySearcher searcher = new DirectorySearcher(entry))
{
searcher.Filter = "(objectClass=*)";
//searcher.Filter = LdapObjectMgr.filterDisabledUsers;
searcher.PropertiesToLoad.Clear();
searcher.PropertiesToLoad.Add(attributeWithRange);
SearchResult results = searcher.FindOne();
foreach (string res in results.Properties.PropertyNames)
{
//list the property names
System.Diagnostics.Debug.WriteLine(res.ToString());
}
if (results.Properties.Contains(attributeWithRange))
{
foreach (object obj in results.Properties[attributeWithRange])
{
//Console.WriteLine(obj.GetType());
if (obj.GetType().Equals(typeof(System.String)))
{
}
else if (obj.GetType().Equals(typeof(System.Int32)))
{
}
//Console.WriteLine(obj.ToString());
list.Add(obj.ToString());
}
if (lastQuery)
{
quitLoop = true;
}
}
else
{
if (lastQuery == false)
{ lastQuery = true; }
else
{ quitLoop = true; }
}
if (!lastQuery)
{
rangeLow = rangeHigh + 1;
rangeHigh = rangeLow + (rangeStep - 1);
}
}
}
while (!quitLoop);
return list;
}
To connect via C# you will need something like this:
DirectoryEntry child = new DirectoryEntry("LDAP://" + domainControllerName + "/" +
objectDn, userName, password);
If you have the domain controller name, the object domain, a user name and a password, you should be good to go.
Just a heads up, you got downvoted because you didn't mention anything that you tried previously.

Rights that is needed to access the Active Directory?

Hi,
I have a service hosten in IIS that runnes this code :
DirectoryEntry objADAM = default(DirectoryEntry);
// Binding object.
DirectoryEntry objGroupEntry = default(DirectoryEntry);
// Group Results.
DirectorySearcher objSearchADAM = default(DirectorySearcher);
// Search object.
SearchResultCollection objSearchResults = default(SearchResultCollection);
// Binding path.
ActiveDirectory result = new ActiveDirectory();
ActiveDirectoryItem treeNode;
// Get the AD LDS object.
try
{
if (pathToAD.Length > 0)
objADAM = new DirectoryEntry(pathToAD);
else
objADAM = new DirectoryEntry();
objADAM.RefreshCache();
}
catch (Exception e)
{
throw e;
}
// Get search object, specify filter and scope,
// perform search.
try
{
objSearchADAM = new DirectorySearcher(objADAM);
objSearchADAM.Filter = "(&(objectClass=group))";
objSearchADAM.SearchScope = SearchScope.Subtree;
objSearchResults = objSearchADAM.FindAll();
}
catch (Exception e)
{
throw e;
}
// Enumerate groups
try
{
if (objSearchResults.Count != 0)
{
//SearchResult objResult = default(SearchResult);
foreach (SearchResult objResult in objSearchResults)
{
objGroupEntry = objResult.GetDirectoryEntry();
result.ActiveDirectoryTree.Add(new ActiveDirectoryItem() { Id = objGroupEntry.Guid, ParentId = objGroupEntry.Parent.Guid, AccountName = objGroupEntry.Name, Type = ActiveDirectoryType.Group, PickableNode = false });
foreach (object child in objGroupEntry.Properties["member"])
{
treeNode = new ActiveDirectoryItem();
var path = "LDAP://" + child.ToString().Replace("/", "\\/");
using (var memberEntry = new DirectoryEntry(path))
{
if (memberEntry.SchemaEntry.Name.CompareTo("group") != 0 && memberEntry.Properties.Contains("sAMAccountName") && memberEntry.Properties.Contains("objectSid"))
{
treeNode.Id = Guid.NewGuid();
treeNode.ParentId = objGroupEntry.Guid;
treeNode.AccountName = memberEntry.Properties["sAMAccountName"][0].ToString();
treeNode.Type = ActiveDirectoryType.User;
treeNode.PickableNode = true;
treeNode.FullName = memberEntry.Properties["Name"][0].ToString();
byte[] sidBytes = (byte[])memberEntry.Properties["objectSid"][0];
treeNode.ObjectSid = new System.Security.Principal.SecurityIdentifier(sidBytes, 0).ToString();
result.ActiveDirectoryTree.Add(treeNode);
}
}
}
}
}
else
{
throw new Exception("No groups found");
}
}
catch (Exception e)
{
throw new Exception(e.Message);
}
return result;
This works fine in my dev enviroment but at a customer we get this exception :
The specified directory service attribute or value does not exist
I supose that this could have to do with the rights to the Active Directory?
What account needs ActiveDirectory and what level of rights is needed?
The account running the thread needs to have read rights to AD. All domain accounts have this permission.
To cut a long story short, verify that the value of HttpContext.Current.User.Identity.Name is a domain account.
If the web application is configured to have anonymous access, then most likely it won't be.

C# Active Directory: Get domain name of user?

I know that this type of question has been asked before, but other methods are failing me right now.
As it stands our windows service polls AD, given an LDAP (i.e. LDAP://10.32.16.80) and a list of usergroups within that AD server to search for.
It retrieves all users within those given groups, recursively searching those groups for more groups as well.
Each user is then added to another applications authenticated users list.
This part of the application is running successfully. However, we're in need of each user's friendly domain name (i.e. the part of their login DOMAIN/username)
So if there is a user that is part of TEST domain, named Steve: TEST/steve is his login.
I'm able to find steve in the AD, however I also need "TEST" to be stored along with his AD information.
Again, I can find 'steve' fine by using a directory searcher and the LDAP IP I'm given, but given the LDAP IP, how can I find the friendly domain name?
When I try the following code I'm given an error when attempting to access the 'defaultNamingContext':
System.Runtime.InteropServices.COMException (0x8007202A): The authentication mechanism is unknown.
Here is the code:
private string SetCurrentDomain(string server)
{
string result = string.Empty;
try
{
logger.Debug("'SetCurrentDomain'; Instantiating rootDSE LDAP");
DirectoryEntry ldapRoot = new DirectoryEntry(server + "/rootDSE", username, password);
logger.Debug("'SetCurrentDomain'; Successfully instantiated rootDSE LDAP");
logger.Debug("Attempting to retrieve 'defaultNamingContext'...");
string domain = (string)ldapRoot.Properties["defaultNamingContext"][0]; //THIS IS WHERE I HIT THE COMEXCEPTION
logger.Debug("Retrieved 'defaultNamingContext': " + domain);
if (!domain.IsEmpty())
{
logger.Debug("'SetCurrentDomain'; Instantiating partitions/configuration LDAP entry");
DirectoryEntry parts = new DirectoryEntry(server + "/CN=Partitions,CN=Configuration," + domain, username, password);
logger.Debug("'SetCurrentDomain'; Successfully instantiated partitions/configuration LDAP entry");
foreach (DirectoryEntry part in parts.Children)
{
if (part.Properties["nCName"] != null && (string)part.Properties["nCName"][0] != null)
{
logger.Debug("'SetCurrentDomain'; Found property nCName");
if ((string)part.Properties["nCName"][0] == domain)
{
logger.Debug("'SetCurrentDomain'; nCName matched defaultnamingcontext");
result = (string)part.Properties["NetBIOSName"][0];
logger.Debug("'SetCurrentDomain'; Found NetBIOSName (friendly domain name): " + result);
break;
}
}
}
}
logger.Debug("finished setting current domain...");
}
catch (Exception ex)
{
logger.Error("error attempting to set domain:" + ex.ToString());
}
return result;
}
edit
I added this sample method in order to attempt a suggestion but am getting an exception: "Unspecified error" when I hit the "FindAll()" call on the searcher.
The string being passed in is: "CN=TEST USER,CN=Users,DC=tempe,DC=ktregression,DC=com"
private string GetUserDomain(string dn)
{
string domain = string.Empty;
string firstPart = dn.Substring(dn.IndexOf("DC="));
string secondPart = "CN=Partitions,CN=Configuration," + firstPart;
DirectoryEntry root = new DirectoryEntry(secondPart, textBox2.Text, textBox3.Text);
DirectorySearcher searcher = new DirectorySearcher(root);
searcher.SearchScope = SearchScope.Subtree;
searcher.ReferralChasing = ReferralChasingOption.All;
searcher.Filter = "(&(nCName=" + firstPart + ")(nETBIOSName=*))";
try
{
SearchResultCollection rs = searcher.FindAll();
if (rs != null)
{
domain = GetProperty(rs[0], "nETBIOSName");
}
}
catch (Exception ex)
{
}
return domain;
This article helped me much to understand how to work with the Active Directory.
Howto: (Almost) Everything In Active Directory via C#
From this point forward, if you require further assitance, please let me know with proper questions in comment, and I shall answer them for you to the best of my knowledge.
EDIT #1
You had better go with this example's filter instead. I have written some sample code to briefly show how to work with the System.DirectoryServices and System.DirectoryServices.ActiveDirectory namespaces. The System.DirectoryServices.ActiveDirectory namespace is used to retrieve information about the domains within your Forest.
private IEnumerable<DirectoryEntry> GetDomains() {
ICollection<string> domains = new List<string>();
// Querying the current Forest for the domains within.
foreach(Domain d in Forest.GetCurrentForest().Domains)
domains.Add(d.Name);
return domains;
}
private string GetDomainFullName(string friendlyName) {
DirectoryContext context = new DirectoryContext(DirectoryContextType.Domain, friendlyName);
Domain domain = Domain.GetDomain(context);
return domain.Name;
}
private IEnumerable<string> GetUserDomain(string userName) {
foreach(string d in GetDomains())
// From the domains obtained from the Forest, we search the domain subtree for the given userName.
using (DirectoryEntry domain = new DirectoryEntry(GetDomainFullName(d))) {
using (DirectorySearcher searcher = new DirectorySearcher()){
searcher.SearchRoot = domain;
searcher.SearchScope = SearchScope.Subtree;
searcher.PropertiesToLoad.Add("sAMAccountName");
// The Filter is very important, so is its query string. The 'objectClass' parameter is mandatory.
// Once we specified the 'objectClass', we want to look for the user whose login
// login is userName.
searcher.Filter = string.Format("(&(objectClass=user)(sAMAccountName={0}))", userName);
try {
SearchResultCollection results = searcher.FindAll();
// If the user cannot be found, then let's check next domain.
if (results == null || results.Count = 0)
continue;
// Here, we yield return for we want all of the domain which this userName is authenticated.
yield return domain.Path;
} finally {
searcher.Dispose();
domain.Dispose();
}
}
}
Here, I didn't test this code and might have some minor issue to fix. This sample is provided as-is for the sake of helping you. I hope this will help.
EDIT #2
I found out another way out:
You have first to look whether you can find the user account within your domain;
If found, then get the domain NetBIOS Name; and
concatenate it to a backslash (****) and the found login.
The example below uses a NUnit TestCase which you can test for yourself and see if it does what you are required to.
[TestCase("LDAP://fully.qualified.domain.name", "TestUser1")]
public void GetNetBiosName(string ldapUrl, string login)
string netBiosName = null;
string foundLogin = null;
using (DirectoryEntry root = new DirectoryEntry(ldapUrl))
Using (DirectorySearcher searcher = new DirectorySearcher(root) {
searcher.SearchScope = SearchScope.Subtree;
searcher.PropertiesToLoad.Add("sAMAccountName");
searcher.Filter = string.Format("(&(objectClass=user)(sAMAccountName={0}))", login);
SearchResult result = null;
try {
result = searcher.FindOne();
if (result == null)
if (string.Equals(login, result.GetDirectoryEntry().Properties("sAMAccountName").Value))
foundLogin = result.GetDirectoryEntry().Properties("sAMAccountName").Value
} finally {
searcher.Dispose();
root.Dispose();
if (result != null) result = null;
}
}
if (!string.IsNullOrEmpty(foundLogin))
using (DirectoryEntry root = new DirectoryEntry(ldapUrl.Insert(7, "CN=Partitions,CN=Configuration,DC=").Replace(".", ",DC="))
Using DirectorySearcher searcher = new DirectorySearcher(root)
searcher.Filter = "nETBIOSName=*";
searcher.PropertiesToLoad.Add("cn");
SearchResultCollection results = null;
try {
results = searcher.FindAll();
if (results != null && results.Count > 0 && results[0] != null) {
ResultPropertyValueCollection values = results[0].Properties("cn");
netBiosName = rpvc[0].ToString();
} finally {
searcher.Dispose();
root.Dispose();
if (results != null) {
results.Dispose();
results = null;
}
}
}
Assert.AreEqual("FULLY\TESTUSER1", string.Concat(netBiosName, "\", foundLogin).ToUpperInvariant())
}
The source from which I inspired myself is:
Find the NetBios Name of a domain in AD
Since I could not find any example code I would like to share my own solution. This will search the parents of the DirectoryEntry object until it hits the domainDNS class.
using System.DirectoryServices;
public static class Methods
{
public static T ldap_get_value<T>(PropertyValueCollection property)
{
object value = null;
foreach (object tmpValue in property) value = tmpValue;
return (T)value;
}
public static string ldap_get_domainname(DirectoryEntry entry)
{
if (entry == null || entry.Parent == null) return null;
using (DirectoryEntry parent = entry.Parent)
{
if (ldap_get_value<string>(parent.Properties["objectClass"]) == "domainDNS")
return ldap_get_value<string>(parent.Properties["dc"]);
else
return ldap_get_domainname(parent);
}
}
}
Use it like this:
string[] _properties = new string[] { "objectClass", "distinguishedName", "samAccountName", "userPrincipalName", "displayName", "mail", "title", "company", "thumbnailPhoto", "useraccountcontrol" };
string account = "my-user-name";
// OR even better:
// string account = "my-user-name#DOMAIN.local";
using (DirectoryEntry ldap = new DirectoryEntry())
{
using (DirectorySearcher searcher = new DirectorySearcher(ldap))
{
searcher.PropertiesToLoad.AddRange(_properties);
if (account.Contains('#')) searcher.Filter = "(userPrincipalName=" + account + ")";
else searcher.Filter = "(samAccountName=" + account + ")";
var user = searcher.FindOne().GetDirectoryEntry();
Console.WriteLine("Name: " + Methods.ldap_get_value<string>(user.Properties["displayName"]));
Console.WriteLine("Domain: " + Methods.ldap_get_domainname(user));
Console.WriteLine("Login: " + Methods.ldap_get_domainname(user) + "\\" + Methods.ldap_get_value<string>(user.Properties["samAccountName"]));
}
}
I haven't got a forest to test it on but in theory this should cut it.
You can retrieve the name of the domain that the current user is on using the Environment.UserDomainName Property.
string domainName;
domainName = System.Environment.UserDomainName;
Maybe not entirely correct but...
DirectoryEntry dirEntry = new DirectoryEntry();
DirectorySearcher dirSearcher = new DirectorySearcher(dirEntry);
dirSearcher.SearchScope = SearchScope.Subtree;
dirSearcher.Filter = string.Format("(&(objectClass=user)(|(cn={0})(sn={0}*)(givenName={0})(sAMAccountName={0}*)))", userName);
var searchResults = dirSearcher.FindAll();
foreach (SearchResult sr in searchResults)
{
var de = sr.GetDirectoryEntry();
string user = de.Properties["SAMAccountName"][0].ToString();
string domain = de.Path.ToString().Split(new [] { ",DC=" },StringSplitOptions.None)[1];
MessageBox.Show(domain + "/" + user);
}
Because the value of de.Path is
LDAP://CN=FullName,DC=domain,DC=local

Categories