Vinc 웃
Vinc 웃

Reputation: 1257

How to use AD Attributes not represented in the Principal Class

The Principal class only have a few AD attributes :

enter image description here

The problem is I need to read a property that is not in the Principal Class...

Here's how I query the AD object :

// create your domain context
PrincipalContext ctx = new PrincipalContext(ContextType.Domain,ConfigurationManager.AppSettings["ADDomain"].ToString(), ConfigurationManager.AppSettings["ADUser"].ToString(), ConfigurationManager.AppSettings["ADPassword"].ToString());

// define a "query-by-example" principal - here, we search for all users
UserPrincipalEXT qbeUser = new UserPrincipalEXT(ctx);

// create your principal searcher passing in the QBE principal    
PrincipalSearcher srch = new PrincipalSearcher(qbeUser);

// find all matches
foreach (var found in srch.FindAll()) //FOUND represent the AD object
{
    ...
}

Is there a way to extend the Principal class to get more AD properties ?

Upvotes: 1

Views: 1870

Answers (2)

marc_s
marc_s

Reputation: 755157

If you're on .NET 3.5 and up and using the System.DirectoryServices.AccountManagement (S.DS.AM) namespace, you can easily extend the existing UserPrincipal class to get at more advanced properties, like Manager etc.

Read all about it here:

Basically, you just define a derived class based on UserPrincipal, and then you define your additional properties you want:

[DirectoryRdnPrefix("CN")]
[DirectoryObjectClass("Person")]
public class UserPrincipalEx : UserPrincipal
{
    // Inplement the constructor using the base class constructor. 
    public UserPrincipalEx(PrincipalContext context) : base(context)
    { }

    // Implement the constructor with initialization parameters.    
    public UserPrincipalEx(PrincipalContext context,
                         string samAccountName,
                         string password,
                         bool enabled) : base(context, samAccountName, password, enabled)
    {} 

    // Create the "Department" property.    
    [DirectoryProperty("department")]
    public string Department
    {
        get
        {
            if (ExtensionGet("department").Length != 1)
                return string.Empty;

            return (string)ExtensionGet("department")[0];
        }
        set { ExtensionSet("department", value); }
    }

    // Create the "Manager" property.    
    [DirectoryProperty("manager")]
    public string Manager
    {
        get
        {
            if (ExtensionGet("manager").Length != 1)
                return string.Empty;

            return (string)ExtensionGet("manager")[0];
        }
        set { ExtensionSet("manager", value); }
    }
}

Now, you can use the "extended" version of the UserPrincipalEx in your code:

using (PrincipalContext ctx = new PrincipalContext(ContextType.Domain))
{
    // Search the directory for the new object. 
    UserPrincipalEx inetPerson = UserPrincipalEx.FindByIdentity(ctx, IdentityType.SamAccountName, "someuser");

    // you can easily access the Manager or Department now
    string department = inetPerson.Department;
    string manager = inetPerson.Manager;
}        

Upvotes: 4

itsme86
itsme86

Reputation: 19526

You can use GetUnderlyingObject() to access additional properties:

if (found.GetUnderlyingObjectType() == typeof(DirectoryEntry))
{
    DirectoryEntry de = (DirectoryEntry)principal.GetUnderlyingObject();
    // Use de.Properties to access additional information
}

Upvotes: 2

Related Questions