I've implemented login through Active Directory credentials in my web application. It first authenticates the user by ValidateCredentials(userName, password)
and then verifies if it exists in certain groups. The unit tests are failing randomly for the same user. I've got a test fixture that contains 22 tests with both correct and wrong values.
I've already tried passing ContextOptions
and username and password for creating PrincipalContext
. I've tried retries after 1 second on fail but no result. I've tried using HostingEnvironment.Impersonate()
;
Method for authentication through AD
public static bool AuthenticateViaAd(string userName, string password)
{
using(var ctx = new PrincipalContext(ContextType.Domain, "AD.DomainName"))
{
return ctx.ValidateCredentials(userName, password);
}
}
Method for verifying UserGroups
public static List<UserRole> GetUserRolesForAdUser(string userName, string password)
{
using (var ctx = new PrincipalContext(ContextType.Domain, "AD.DomainName", userName, password))
{
// find a user
var userId = UserPrincipal.FindByIdentity(ctx, userName);
if (userId == null)
return NoRoles;
// find the group in question
var groupDataProcessor = GroupPrincipal.FindByIdentity(ctx, Consts.AdGroupDataProcessors) ??
throw new InvalidOperationException("Data Processor group is not present. Please contact IT.");
var groupSupport = GroupPrincipal.FindByIdentity(ctx, Consts.AdGroupSupport) ??
throw new InvalidOperationException("Support group is not present. Please contact IT.");
var groupSales = GroupPrincipal.FindByIdentity(ctx, Consts.AdGroupSales) ??
throw new InvalidOperationException("Sales group is not present. Please contact IT.");
// check if user is member of that group
if (userId.IsMemberOf(groupDataProcessor))
return DataProcessorsRoles;
if (userId.IsMemberOf(groupSupport))
return SupportRoles;
if (userId.IsMemberOf(groupSales))
return SalesRoles;
return NoRoles;
}
}
Error message in GetUserRolesForAdUser
System.DirectoryServices.DirectoryServicesCOMException : The user name or password is incorrect.
at System.DirectoryServices.DirectoryEntry.Bind(Boolean throwIfFail)
at System.DirectoryServices.DirectoryEntry.Bind()
at System.DirectoryServices.DirectoryEntry.get_AdsObject()
at System.DirectoryServices.PropertyValueCollection.PopulateList()
at System.DirectoryServices.PropertyValueCollection..ctor(DirectoryEntry entry, String propertyName)
at System.DirectoryServices.PropertyCollection.get_Item(String propertyName)
at System.DirectoryServices.AccountManagement.PrincipalContext.DoLDAPDirectoryInitNoContainer()
at System.DirectoryServices.AccountManagement.PrincipalContext.DoDomainInit()
at System.DirectoryServices.AccountManagement.PrincipalContext.Initialize()
at System.DirectoryServices.AccountManagement.PrincipalContext.get_QueryCtx()
at System.DirectoryServices.AccountManagement.Principal.FindByIdentityWithTypeHelper(PrincipalContext context, Type principalType, Nullable`1 identityType, String identityValue, DateTime refDate)
at System.DirectoryServices.AccountManagement.Principal.FindByIdentityWithType(PrincipalContext context, Type principalType, String identityValue)
at System.DirectoryServices.AccountManagement.UserPrincipal.FindByIdentity(PrincipalContext context, String identityValue)