简体   繁体   English

使用c#中的vpn进行活动目录身份验证

[英]Active directory authentication using vpn in c#

I am developing a web application that authenticate the user against an Active Directory Server. 我正在开发一个Web应用程序,用于根据Active Directory服务器对用户进行身份验证。 Now if I run my code from the development PC under the domain of that AD server, my code is running smoothly. 现在如果我从该AD服务器域下的开发PC运行我的代码,我的代码运行顺利。 We need to run the code from a totally different network using VPN and here the development PC is not into that AD. 我们需要使用VPN从完全不同的网络运行代码,这里开发PC不在那个AD中。 I am getting following error while trying to access the AD server. 尝试访问AD服务器时出现以下错误。

The specified domain either does not exist or could not be contacted. 指定的域不存在或无法联系。

My VPN is working fine. 我的VPN工作正常。 I could access remote desktops using this VPN. 我可以使用此VPN访问远程桌面。 I know a little tweak is required to solve the problem but could not find it. 我知道需要一些调整来解决问题,但找不到它。 I went through following links but could not find any solution. 我通过以下链接但找不到任何解决方案。

  1. Domain Authentication from .NET Client over VPN 通过VPN从.NET客户端进行域身份验证

  2. How do I get the Current User identity for a VPN user in a Windows forms app? 如何在Windows窗体应用程序中获取VPN用户的当前用户身份?

Following is my settings in web.config 以下是我在web.config设置

<appSettings>
   <add key="LDAPPath" value="LDAP://DC=MYSERVER,DC=COM" />
   <add key="ADGroupName" value="Analyst"/>
</appSettings>

and here is my code 这是我的代码

public class LdapAuthentication
{
    private string _path;
    private string _filterAttribute;

    public LdapAuthentication()
    {
        _path = System.Configuration.ConfigurationManager.AppSettings["LDAPPath"].ToString();
    }

    public bool IsAuthenticated(string username, string pwd)
    {
        try
        {
            DirectoryEntry entry = new DirectoryEntry(_path, username, pwd);

            entry.Path = _path;
            entry.Username = username;
            entry.Password = pwd;

            // Bind to the native AdsObject to force authentication.
            object obj = entry.NativeObject;

            DirectorySearcher search = new DirectorySearcher(entry);

            search.Filter = "(SAMAccountName=" + username + ")";
            search.PropertiesToLoad.Add("cn");
            SearchResult result = search.FindOne();

            if (null == result)
            {
                return false;
            }

            // Update the new path to the user in the directory.
            _path = result.Path;
            _filterAttribute = (string)result.Properties["cn"][0];
        }
        catch (Exception ex)
        {
            throw new Exception("Error authenticating user. " + ex.Message);
        }

        return true;
    }
}

Any help would be appreciated. 任何帮助,将不胜感激。 Thank you. 谢谢。

I had a similar, though simpler problem. 我有一个类似但更简单的问题。 I had success in using the following code: 我成功使用了以下代码:

private bool DoLogin(string userName, string password)
{
    using (PrincipalContext pc = new PrincipalContext(ContextType.Domain, "DomainName.com")) {
        bool isValid = pc.ValidateCredentials(userName, password);
        if (isValid) {
            // authenticated
            ...
            return true;
        }
        else {
            // invalid credentials
            ...
            return false;
        }
    }
}

Using the ".com" at the end of the domain name was important to get it working for me. 使用域名末尾的“.com”对于让它为我工作非常重要。 Without it I got the same symptoms you describe. 没有它我会得到你描述的相同症状。

I've just been grappling with this for a couple of hours. 我刚刚在这里努力了几个小时。 No problems when on the network, lots of problems when connecting via VPN. 在网络上没有问题,通过VPN连接时出现很多问题。 It seems that when you are connecting over a VPN, the 'connection string' for DirectoryEntry has to be a lot more precise. 看来,当您通过VPN连接时,DirectoryEntry的“连接字符串”必须更加精确。 I finally got it to work with an LDAP address/connection string like this: 我终于使用了这样的LDAP地址/连接字符串:

LDAP://ip_of_primary_domain_controller/fully qualified path of the container object where the binding user is located

So for example something like this worked for me: 所以像这样的东西对我有用:

DirectoryEntry directoryEntry = new DirectoryEntry(
      "LDAP://192.168.0.20/OU=Service Accounts,OU=Admin Accounts,DC=myserver,DC=com",
      "username@myserver.com", "password"); 

... where "username@myserver.com" is located in OU=Service Accounts,OU=Admin Accounts,DC=myserver,DC=com. ...其中“username@myserver.com”位于OU =服务帐户,OU =管理员帐户,DC = myserver,DC = com。 If you use SysInternals ADExplorer (or similar) to search for your username, it will tell you the correct fully qualified path for the container. 如果您使用SysInternals ADExplorer(或类似)来搜索您的用户名,它将告诉您容器的正确完全限定路径。

See here for a long answer about exactly whats should be in the 'connection string': https://serverfault.com/a/130556 请参阅此处以获取有关“连接字符串”中的确切内容的详细答案: https//serverfault.com/a/130556

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM