本文引用下面的 Microsoft.NET 框架类库名称空间:
  • System.Text
  • System.DirectoryServices
  • System.Security.Principal
  • System.Web.Security
本分步指南演示如何将 ASP.NET 应用程序可以使用 Forms 身份验证允许用户使用轻型目录访问协议 (LDAP) 身份验证 Active Directory。 用户身份验证中,并重定向之后,您可以 Application _ AuthenticateRequest 方法用于 Global.asax 文件的整个请求过程流 HttpContext.User 属性存储 GenericPrincipal 对象。

在 Visual C#.NET 创建 ASP.NET Web 应用程序请按照下列步骤创建名为 FormsAuthAd 在 Visual C#.NET 中的一个新 ASP.NET Web 应用程序:

  1. 启动 Microsoft Visual Studio.NET。
  2. 文件 菜单上指向 新建 ,然后单击 项目
  3. 单击 项目类型 下的 Visual C# 项目 ,然后单击 模板 下的 ASP.NET Web 应用程序
  4. 位置 框中将 WebApplication 1 替换为 FormsAuthAd 。
  5. 单击 确定
  6. 右击解决方案资源管理器 引用 节点,然后单击 添加引用
  7. 添加引用 对话框 .NET 选项卡中,单击 System.DirectoryServices.dll ,单击 选择 ,然后单击 确定

编写身份验证代码请按照下列步骤创建新的类文件名为 LdapAuthentication.cs:

  1. 在解决方案资源管理器右键单击该项目节点,指向 添加 ,然后单击 添加新项
  2. 单击 模板 下的
  3. 名称 框中键入 LdapAuthentication.cs ,然后单击了此操作的 打开
  4. LdapAuthentication.cs 文件中的将现有代码替换为下面的代码
Code
 1using System;
 2using System.Text;
 3using System.Collections;
 4using System.DirectoryServices;
 5
 6namespace FormsAuth
 7{    
 8  public class LdapAuthentication
 9  {
10    private String _path;
11    private String _filterAttribute;
12
13    public LdapAuthentication(String path)
14    {
15      _path = path;
16    }
17        
18    public bool IsAuthenticated(String domain, String username, String pwd)
19    {
20      String domainAndUsername = domain + @"\" + username;
21      DirectoryEntry entry = new DirectoryEntry(_path, domainAndUsername, pwd);
22            
23      try
24      {    //Bind to the native AdsObject to force authentication.            
25         Object obj = entry.NativeObject;
26
27    DirectorySearcher search = new DirectorySearcher(entry);
28
29    search.Filter = "(SAMAccountName=" + username + ")";
30    search.PropertiesToLoad.Add("cn");
31    SearchResult result = search.FindOne();
32
33    if(null == result)
34    {
35        return false;
36    }
37
38    //Update the new path to the user in the directory.
39    _path = result.Path;
40    _filterAttribute = (String)result.Properties["cn"][0];
41      }
42      catch (Exception ex)
43      {
44        throw new Exception("Error authenticating user. " + ex.Message);
45      }
46
47    return true;
48     }
49
50     public String GetGroups()
51     {
52       DirectorySearcher search = new DirectorySearcher(_path);
53       search.Filter = "(cn=" + _filterAttribute + ")";
54       search.PropertiesToLoad.Add("memberOf");
55       StringBuilder groupNames = new StringBuilder();
56
57       try
58       {
59         SearchResult result = search.FindOne();
60
61     int propertyCount = result.Properties["memberOf"].Count;
62
63        String dn;
64     int equalsIndex, commaIndex;
65                
66     for(int propertyCounter = 0; propertyCounter < propertyCount; propertyCounter++)
67     {
68       dn = (String)result.Properties["memberOf"][propertyCounter];
69
70           equalsIndex = dn.IndexOf("=", 1);
71       commaIndex = dn.IndexOf(",", 1);
72       if(-1 == equalsIndex)
73       {
74         return null;
75            }
76
77           groupNames.Append(dn.Substring((equalsIndex + 1), (commaIndex - equalsIndex) - 1));
78       groupNames.Append("|");
79
80         }
81       }
82       catch(Exception ex)
83       {
84         throw new Exception("Error obtaining group names. " + ex.Message);
85       }            
86       return groupNames.ToString();
87     }
88   }
89}
90

身份验证代码接受域、 用户名、 一个的密码和 Active Directory 中树的路径。 此代码使用 LDAP 目录提供程序。

Logon.aspx 页中的代码调用 LdapAuthentication.IsAuthenticated 方法,并从用户收集的凭据中传递。 DirectoryEntry 对象则,创建路径目录树、 该用户名和密码。 在用户名必须以"domain\username"格式。 DirectoryEntry 对象然后尝试通过获取 NativeObject 属性强制 AdsObject 绑定。 如果成功,用户的 CN 属性获取通过创建一个 DirectorySearcher 对象以及筛选 SAMAccountName 。 对用户进行身份验证后,则该 IsAuthenticated 方法返回 True

要获取用户所属的组的列表,此代码将调用 LdapAuthentication.GetGroups 方法。 LdapAuthentication.GetGroups 方法获取用户所属通过创建一个 DirectorySearcher 对象以及根据 memberOf 属性进行筛选的安全组和通讯组的列表。 此方法返回由管道 (|) 分隔组的列表。

请注意 LdapAuthentication.GetGroups 方法操纵和截断字符串。 这减少了身份验证 Cookie 中存储的字符串的长度。 如果字符串未被截断,每个组的格式显示如下。

CN=...,...,DC=domain,DC=com

这可以创建一个很长的字符串。 如果此字符串的长度大于 cookie 的长度,浏览器可能不接受该身份验证 Cookie,并您将被重定向到登录页。 但是,如果您处于多域环境时,可能不得不保留域名称与组名称,因为不同的域中的组可以有相同的组名称。 您需要保留域名称来彼此区分一个组。

大多数浏览器支持的最多为 4096 字节的 Cookie。 如果该字符串可能可能会超出 Cookie 的长度,可能要在 ASP.NET 缓存对象或数据库中存储组信息。 或者,可能要加密组信息,并将此信息存储在隐藏的窗体字段。

编写 Global.asax 代码Global.asax 文件中的该代码步指南提供了的 Application _ AuthenticateRequest 事件处理程序。 此事件处理程序从 Context.Request.Cookies 集合中检索身份验证 Cookie,以解密该 cookie,并检索 FormsAuthenticationTicket.UserData 属性中存储组的列表。 这些组显示在 Logon.aspx 页中创建的管道分隔列表中。

代码分析字符串数组创建 GenericPrincipal 对象中的该字符串。 创建 GenericPrincipal 对象后,此对象将被置于 HttpContext.User 属性。

  1. 在解决方案资源管理器右键单击 Global.asax ,然后单击 查看代码
  2. 代码的-隐藏 Global.asax.cs 文件顶部添加以下代码: using System.Web.Security;using System.Security.Principal;
  3. Application _ AuthenticateRequest 替换为下面的代码的现有空事件处理程序
Code
 1void Application_AuthenticateRequest(Object sender, EventArgs e)
 2{
 3  String cookieName = FormsAuthentication.FormsCookieName;
 4  HttpCookie authCookie = Context.Request.Cookies[cookieName];
 5
 6  if(null == authCookie)
 7  {//There is no authentication cookie.
 8    return;
 9  }    
10        
11  FormsAuthenticationTicket authTicket = null;
12    
13  try
14  {
15    authTicket = FormsAuthentication.Decrypt(authCookie.Value);
16  }
17  catch(Exception ex)
18  {
19    //Write the exception to the Event Log.
20    return;
21  }
22    
23  if(null == authTicket)
24  {//Cookie failed to decrypt.
25    return;        
26  }        
27    
28  //When the ticket was created, the UserData property was assigned a
29  //pipe-delimited string of group names.
30  String[] groups = authTicket.UserData.Split(new char[]{'|'});
31
32  //Create an Identity.
33  GenericIdentity id = new GenericIdentity(authTicket.Name, "LdapAuthentication");
34    
35  //This principal flows throughout the request.
36  GenericPrincipal principal = new GenericPrincipal(id, groups);
37
38  Context.User = principal;
39    
40}
  1. 修改 Web.config 文件在此部分中,您配置在 <forms><authentication><authorization>在 Web.config 文件中的元素。 用这些的更改只有经过身份验证的用户可以访问应用程序,,并且未经身份验证的请求重定向到 Logon.aspx 页。 您可以修改此配置为允许仅特定用户和组访问应用程序。

    Web.config 文件中现有代码替换为下面的代码中。

    Code
     1<?xml version="1.0" encoding="utf-8" ?>
     2<configuration>    
     3  <system.web>
     4    <authentication mode="Forms">
     5      <forms loginUrl="logon.aspx" name="adAuthCookie" timeout="10" path="/" >
     6      </forms>
     7    </authentication>    
     8    <authorization>    
     9      <deny users="?" />
    10      <allow users="*" />
    11    </authorization>    
    12    <identity impersonate="true" />
    13  </system.web>
    14</configuration>

    请注意 配置元素。 这将导致 ASP.NET 模拟配置为匿名帐户从 Microsoft Internet Information Services (IIS) 的帐户。 因这种配置在配置的帐户的安全上下文中运行此应用程序的所有请求。 用户提供在 Active 的 Directory 身份验证的凭据,但访问 Active Directory 的帐户是配置的帐户。

    为匿名身份验证配置 IIS要配置 IIS 为匿名身份验证,请执行下列步骤:

  2. IIS 中, 展开计算机节点,您的服务器,展开 网站 ,展开 默认网站 ,右键单击 FormsAuthAd ,然后单击 属性 。
  3. 单击 目录安全选项卡 中,然后单击在 匿名访问和身份验证控制 下的 编辑 。
  4. 请应用程序的匿名帐户具有 Active Directory 的权限的帐户。
  5. 单击以清除允许 IIS 控制密码复选框。
  6. 在的身份验证访问 ” 部分取消选中的集成的 Windows 身份验证 ” 复选框。
  7. 单击确定。
  8. 单击应用

默认 IUSR _ computername 帐户没有 Active Directory 的权限。

创建 Logon.aspx 页请按照下列步骤创建名为 Logon.aspx 的新 ASP.NET Web 窗体:

  1. 在解决方案资源管理器右键单击该项目节点,指向 添加 ,然后单击 添加 Web 窗体
  2. 名称 框中键入 Logon.aspx ,,然后单击了此操作的 打开
  3. 在解决方案资源管理器右键单击 Logon.aspx ,然后单击 视图设计器
  4. 单击 HTML 选项卡在设计器中。
  5. Replace the existing code with the following code.
    Code
     1<%@ Page language="c#" AutoEventWireup="true" %>
     2<%@ Import Namespace="FormsAuth" %>
     3<html>
     4  <body>    
     5    <form id="Login" method="post" runat="server">
     6      <asp:Label ID="Label1" Runat=server >Domain:</asp:Label>
     7      <asp:TextBox ID="txtDomain" Runat=server ></asp:TextBox><br>    
     8      <asp:Label ID="Label2" Runat=server >Username:</asp:Label>
     9      <asp:TextBox ID=txtUsername Runat=server ></asp:TextBox><br>
    10      <asp:Label ID="Label3" Runat=server >Password:</asp:Label>
    11      <asp:TextBox ID="txtPassword" Runat=server TextMode=Password></asp:TextBox><br>
    12      <asp:Button ID="btnLogin" Runat=server Text="Login" OnClick="Login_Click"></asp:Button><br>
    13      <asp:Label ID="errorLabel" Runat=server ForeColor=#ff3300></asp:Label><br>
    14      <asp:CheckBox ID=chkPersist Runat=server Text="Persist Cookie" />
    15    </form>    
    16  </body>
    17</html>
    18<script runat=server>
    19void Login_Click(Object sender, EventArgs e)
    20{
    21  String adPath = "LDAP://corp.com"; //Fully-qualified Domain Name
    22  LdapAuthentication adAuth = new LdapAuthentication(adPath);
    23  try
    24  {
    25    if(true == adAuth.IsAuthenticated(txtDomain.Text, txtUsername.Text, txtPassword.Text))
    26    {
    27      String groups = adAuth.GetGroups();
    28
    29      //Create the ticket, and add the groups.
    30      bool isCookiePersistent = chkPersist.Checked;
    31      FormsAuthenticationTicket authTicket = new FormsAuthenticationTicket(1,  txtUsername.Text,
    32    DateTime.Now, DateTime.Now.AddMinutes(60), isCookiePersistent, groups);
    33    
    34      //Encrypt the ticket.
    35      String encryptedTicket = FormsAuthentication.Encrypt(authTicket);
    36        
    37      //Create a cookie, and then add the encrypted ticket to the cookie as data.
    38      HttpCookie authCookie = new HttpCookie(FormsAuthentication.FormsCookieName, encryptedTicket);
    39
    40      if(true == isCookiePersistent)
    41    authCookie.Expires = authTicket.Expiration;
    42                
    43      //Add the cookie to the outgoing cookies collection.
    44      Response.Cookies.Add(authCookie);        
    45
    46      //You can redirect now.
    47      Response.Redirect(FormsAuthentication.GetRedirectUrl(txtUsername.Text, false));
    48    }
    49    else
    50    {
    51      errorLabel.Text = "Authentication did not succeed. Check user name and password.";
    52    }
    53  }
    54  catch(Exception ex)
    55  {
    56    errorLabel.Text = "Error authenticating. " + ex.Message;
    57  }
    58}
    59</script>
  6. 修改路径指向您的 LDAP 目录服务器 Logon.aspx 页中。

Logon.aspx 页是从用户和调用方法收集信息, LdapAuthentication 类一页。 代码对用户进行身份验证,并获取组的列表之后,代码创建一个 FormsAuthenticationTicket 对象,加密票证、 添加加密的票证一个 Cookie,将 Cookie 添加到 HttpResponse.Cookies 集合中,然后将请求重定向到最初请求的 URL。

修改 WebForm 1.aspx 页WebForm 1.aspx 页是原来请求的页。 当用户请求该页时, 将请求重定向到在 Logon.aspx 页。 该请求进行身份验证后,请求将被重定向到 WebForm 1.aspx 页中。

  1. 在解决方案资源管理器右键单击 WebForm 1.aspx ,然后单击 视图设计器
  2. 单击 HTML 选项卡在设计器中。
  3. 现有代码替换为以下 code. 
    Code
     1<%@ Page language="c#" AutoEventWireup="true" %>
     2<%@ Import Namespace="System.Security.Principal" %>
     3<html>
     4  <body>    
     5    <form id="Form1" method="post" runat="server">
     6      <asp:Label ID="lblName" Runat=server /><br>
     7      <asp:Label ID="lblAuthType" Runat=server />
     8    </form>    
     9  </body>
    10</html>
    11<script runat=server>
    12void Page_Load(Object sender, EventArgs e)
    13{
    14  lblName.Text = "Hello " + Context.User.Identity.Name + ".";
    15  lblAuthType.Text = "You were authenticated using " +   Context.User.Identity.AuthenticationType + ".";
    16}
    17</script>
  4. 保存所有的文件,并再编译该项目。
  5. 请求 WebForm 1.aspx 页。 请注意您将被重定向到 Logon.aspx。
  6. 键入登录的凭据,然后单击 提交 。 当您将被重定向到 WebForm 1.aspx 时, 请注意您的用户名出现和该 LdapAuthentication 是身份验证类型为 Context.User.AuthenticationType 属性。

请注意 Microsoft 建议您使用安全套接字层 (SSL) 加密使用 Forms 身份验证时。 这是因为用户标识基于该身份验证 cookie,并且此应用程序上的 SSL 加密防止任何人破坏身份验证 Cookie 和任何其他正在传输的重要信息。

转载于:https://www.cnblogs.com/allenlizq/archive/2009/02/20/1395200.html

如何验证 Active Directory 使用表单身份验证和 Visual C#.NET相关推荐

  1. 【JSP/SERVLET】Tomcat内置表单身份验证

    一.概述 前面是扯犊子的,JSP/SERVLET基于HTTP规范,提供了几种安全支持,BASIC.DIGEST.FORM.CLIENT-CERT,本文主要介绍一下FORM的安全支持开发,文末有一个小d ...

  2. 黑帽python第二版(Black Hat Python 2nd Edition)读书笔记 之 第五章 WEB黑客(4)暴力破解HTML表单身份验证

    黑帽python第二版(Black Hat Python 2nd Edition)读书笔记 之 第五章 WEB黑客(4)暴力破解HTML表单身份验证 文章目录 黑帽python第二版(Black Ha ...

  3. 通过LDAP验证Active Directory服务

    http://www.cnblogs.com/icuit/archive/2010/06/10/1755575.html 这一周做LDAP做得头都大了.现在终于有点头绪了,记录一下,以备后用. LDA ...

  4. GOOGLE ADSENSE广告联盟收不到PIN码_快速表单身份验证PIN码方法

    在自己的网站或者博客上投放Google Adsense广告是目前很多站长不错的赚钱途径.尤其是Google Adsense不仅单价高.而且信誉好.支付稳定等天然优势让国内众多广告联盟黯然失色.在流量有 ...

  5. ASP.NET在IE10中Form表单身份验证失效问题解决方法

    我的系统遇到了这个问题,还好有好心网友发布了一篇文章: ---------网上找的原文如下--------------------------- IE10中Session丢失问题引起众多业内人士的关注 ...

  6. ASP.NET 中的表单身份验证(Forms Authentication)

    表单验证可以通使用一个登录页面验证用户的用户名和密码.未通过验证的请求会被重定向到登录页面,要求用户输入其凭据信息(同常是用户名和密码).如果请求通过验证,系统将签发一个身份验证票据,在用户会话期间, ...

  7. 表单身份验证(受保护的目录)

    根目录下的 web.config <authentication mode="Forms">   <forms name=".COOKIEDEMO&qu ...

  8. java ldap操作实例_Java Spring Security示例教程中的2种设置LDAP Active Directory身份验证的方法...

    java ldap操作实例 LDAP身份验证是世界上最流行的企业应用程序身份验证机制之一,而Active Directory (Microsoft为Windows提供的LDAP实现)是另一种广泛使用的 ...

  9. Java Spring Security示例教程中的2种设置LDAP Active Directory身份验证的方法

    LDAP身份验证是全球范围内最流行的企业应用程序身份验证机制之一,而Active Directory (Microsoft针对Windows的LDAP实现)是另一种广泛使用的LDAP服务器. 在许多项 ...

最新文章

  1. 后盾网lavarel视频项目---vue实现动态添加和删除板块
  2. 使用实例_EM菌使用实例
  3. BZOJ3527: [Zjoi2014]力 [FFT]
  4. [vagrant]vagrant centos静态ip设置
  5. vue中,format与value-format比较
  6. 数据结构最佳路径代码_【微服务】149:商品数据结构
  7. 隐含社交信任度和基于情感的方法的推荐系统
  8. 系统报 “client没有所需的特权” 的解决方法
  9. jquery 后代 children, find方法
  10. 360服务器自动获取设置,360推“史上最严重安全漏洞”自动检测工具 用户一键获取补丁...
  11. C++ QT学习之路----VS2017+QT环境搭建
  12. gmssl编译linux,linux 编译安装GmSSL记录
  13. 2019年小米软件开发《异数》笔试题
  14. ico 图标 生成 工具 网站
  15. 电脑测试软件 免安装,Keyboard Test Utility:电脑必备键盘测试软件,小体积、免安装...
  16. 人工智能算法(一)进化算法
  17. 吃糖果游戏(tyvj 1567)
  18. 【问题解决方法】java词云库kumo色差
  19. 双重检查锁与单例模式
  20. 用python判断闰年

热门文章

  1. 温故而知新-面向对象的PHP
  2. 【翻译】TCP backlog在Linux中的工作原理
  3. click事件延迟300ms,处理方法-----FastClick
  4. ios UIScrollView 中控件自动增加间隔
  5. MySQL批量插入数据的几种方法
  6. 转载自csdn SQL SERVER 与ACCESS、EXCEL的数据转换
  7. 江南山区腊味香 年味浓
  8. spring cloud微服务分布式云架构 - 整合企业架构的技术点
  9. Java EE(五)
  10. ZZUOJ1196: 单调数