.NET 4.5 Błąd w UserPrincipal.FindByIdentity (System.DirectoryServices.AccountManagement)

Podczas testowania naszej aplikacji .NET 4.0 w wersji .NET 4.5 napotkaliśmy problem zFindByIdentity metoda dlaUserPrincipal. Poniższy kod działa, gdy działa w środowisku wykonawczym .NET 4.0, ale nie działa w środowisku .NET 4.5:

[Test]
public void TestIsAccountLockedOut()
{
    const string activeDirectoryServer = "MyActiveDirectoryServer";
    const string activeDirectoryLogin = "MyADAccount@MyDomain";
    const string activeDirectoryPassword = "MyADAccountPassword";
    const string userAccountToTest = "TestUser@MyDomain";
    const string userPasswordToTest = "WRONGPASSWORD";

    var principalContext = new PrincipalContext(ContextType.Domain, activeDirectoryServer, activeDirectoryLogin, activeDirectoryPassword);

    var isAccountLockedOut = false;
    var isAuthenticated = principalContext.ValidateCredentials(userAccountToTest, userPasswordToTest, principalContext.Options);
    if (!isAuthenticated)
    {
        // System.DirectoryServices.AccountManagement.PrincipalOperationException : Information about the domain could not be retrieved (1355).
        using (var user = UserPrincipal.FindByIdentity(principalContext, IdentityType.UserPrincipalName, userAccountToTest))
        {
            isAccountLockedOut = (user != null) && user.IsAccountLockedOut();
        }
    }
    Assert.False(isAuthenticated);
    Assert.False(isAccountLockedOut);
}

Oto ślad stosu wyjątków:

System.DirectoryServices.AccountManagement.PrincipalOperationException : Information about the domain could not be retrieved (1355).
at System.DirectoryServices.AccountManagement.Utils.GetDcName(String computerName, String domainName, String siteName, Int32 flags)   at System.DirectoryServices.AccountManagement.ADStoreCtx.LoadDomainInfo()   at 
System.DirectoryServices.AccountManagement.ADStoreCtx.get_DnsDomainName()   at System.DirectoryServices.AccountManagement.ADStoreCtx.GetAsPrincipal(Object storeObject, Object discriminant)   at 
System.DirectoryServices.AccountManagement.ADStoreCtx.FindPrincipalByIdentRefHelper(Type principalType, String urnScheme, String urnValue, DateTime referenceDate, Boolean useSidHistory)   at 
System.DirectoryServices.AccountManagement.ADStoreCtx.FindPrincipalByIdentRef(Type principalType, String urnScheme, String urnValue, DateTime referenceDate)   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, IdentityType identityType, String identityValue)   at 
System.DirectoryServices.AccountManagement.UserPrincipal.FindByIdentity(PrincipalContext context, IdentityType identityType, String identityValue)   

Czy ktoś widział i rozwiązał ten problem? Jeśli nie, czy jest lepszy sposób na sprawdzenieIsAccountLockedOut status konta Active Directory?

Dla odniesienia wszystkie nasze maszyny testowe znajdują się w tej samej podsieci. Istnieją oddzielne serwery ActiveDirectory z systemem Windows Server 2003, 2008 i 2012 w różnych trybach funkcjonalności domeny (patrz poniżej). Kod działa z komputerów z uruchomionym .NET 4.0, ale nie działa z komputerów z uruchomionym .NET 4.5.

Trzy maszyny .NET z których uruchomiliśmy kod to:
- Windows 7 z uruchomionym .NET 4.0
- Windows Vista z systemem .NET 4.5
- Windows Server 2012 z systemem .NET 4.5

Serwery Active Directory, które wypróbowaliśmy, to:
- Windows 2003 z trybem funkcjonalnym domeny AD ustawionym na macierzysty system Windows 2000
- Windows 2003 z trybem funkcjonalnym domeny AD ustawionym na Windows Server 2003
- Windows 2008 z trybem funkcjonalnym domeny AD ustawionym na macierzysty system Windows 2000
- Windows 2008 z trybem funkcjonalnym domeny AD ustawionym na Windows Server 2003
- Windows 2008 z trybem funkcjonalnym domeny AD ustawionym na Windows Server 2008
- Windows 2012 z trybem funkcjonalnym domeny AD ustawionym na Windows 2012

Wszystkie te serwery Active Directory są skonfigurowane jako prosty, pojedynczy las, a komputery klienckie nie są częścią domeny. Nie są one używane do żadnej innej funkcji niż testowanie tego zachowania i nie uruchamiają niczego innego niż Active Directory.

EDIT - 9 października 2012

Dziękujemy wszystkim, którzy odpowiedzieli. Poniżej znajduje się klient wiersza polecenia C #, który demonstruje problem, oraz krótkoterminowe obejście, które zidentyfikowaliśmy, a które nie wymagało od nas zmiany niczego w konfiguracji Active Directory i DNS. Wydaje się, że wyjątek jest generowany tylko raz z instancją PrincipalContext. Dołączyliśmy wyjścia do komputera .NET 4.0 (Windows 7) i komputera .NET 4.5 (Windows Vista).

using System;
using System.DirectoryServices.AccountManagement;

namespace ADBug
{
    class Program
    {
        static void Main(string[] args)
        {
            const string activeDirectoryServer = "MyActiveDirectoryServer";
            const string activeDirectoryLogin = "MyADAccount";
            const string activeDirectoryPassword = "MyADAccountPassword";
            const string validUserAccount = "[email protected]";
            const string unknownUserAccount = "[email protected]";

            var principalContext = new PrincipalContext(ContextType.Domain, activeDirectoryServer, activeDirectoryLogin, activeDirectoryPassword);

            // .NET 4.0 - First attempt with a valid account finds the user
            // .NET 4.5 - First attempt with a valid account fails with a PrincipalOperationException
            TestFindByIdentity(principalContext, validUserAccount, "Valid Account - First Attempt");
            // Second attempt with a valid account finds the user
            TestFindByIdentity(principalContext, validUserAccount, "Valid Account - Second Attempt");
            // First attempt with an unknown account does not find the user
            TestFindByIdentity(principalContext, unknownUserAccount, "Unknown Account - First Attempt");
            // Second attempt with an unknown account does not find the user (testing false positive)
            TestFindByIdentity(principalContext, unknownUserAccount, "Unknown Account - Second Attempt");
            // Subsequent attempt with a valid account still finds the user
            TestFindByIdentity(principalContext, validUserAccount, "Valid Account - Third Attempt");
        }

        private static void TestFindByIdentity(PrincipalContext principalContext, string userAccountToTest, string message)
        {
            var exceptionThrown = false;
            var userFound = false;
            try
            {
                using (var user = UserPrincipal.FindByIdentity(principalContext, IdentityType.UserPrincipalName, userAccountToTest))
                {
                    userFound = (user != null);
                }
            }
            catch (PrincipalOperationException)
            {
                exceptionThrown = true;
            }
            Console.Out.WriteLine(message + " - Exception Thrown  = {0}", exceptionThrown);
            Console.Out.WriteLine(message + " - User Found = {1}", userAccountToTest, userFound);
        }
    }
}

Wyjście .NET 4.0

Valid Account - First Attempt - Exception Thrown  = False
Valid Account - First Attempt - User Found = True
Valid Account - Second Attempt - Exception Thrown  = False
Valid Account - Second Attempt - User Found = True
Unknown Account - First Attempt - Exception Thrown  = False
Unknown Account - First Attempt - User Found = False
Unknown Account - Second Attempt - Exception Thrown  = False
Unknown Account - Second Attempt - User Found = False
Valid Account - Third Attempt - Exception Thrown  = False
Valid Account - Third Attempt - User Found = True

Wyjście .NET 4.5

Valid Account - First Attempt - Exception Thrown  = True
Valid Account - First Attempt - User Found = False
Valid Account - Second Attempt - Exception Thrown  = False
Valid Account - Second Attempt - User Found = True
Unknown Account - First Attempt - Exception Thrown  = False
Unknown Account - First Attempt - User Found = False
Unknown Account - Second Attempt - Exception Thrown  = False
Unknown Account - Second Attempt - User Found = False
Valid Account - Third Attempt - Exception Thrown  = False
Valid Account - Third Attempt - User Found = True

questionAnswers(3)

yourAnswerToTheQuestion