位置:海鸟网 > IT > ASP.NET >

ATL Server 与 ASP.NET

     下载本文的代码:ASPColumn0311.exe (534KB)
  *
  本页内容
  ASP.NET 究竟是什么?ASP.NET 究竟是什么?
  ATL Server 有何不同?ATL Server 有何不同?
  ATL Server 与 ASP .NETATL Server 与 ASP .NET
  ASPX 文件与 SRFASPX 文件与 SRF
  “固有”对象“固有”对象
  管理 UI 元素管理 UI 元素
  会话状态会话状态
  小结小结
  
  Web 服务器的任务就是接受传入的 HTTP 请求,并返回一些对呼叫方有用的信息(不论呼叫方是人,或者是 Web 服务时的机器)。Windows 包含有处理请求的成熟结构 — IIS 及其相关扩展。但是,从头开始设计 IIS 是很单调乏味的,并且容易出错。管理 HTTP 请求的一种较好的方法就是利用位于 IIS 顶部的一种框架来管理。本月我将比较两种创建 Windows Web 应用程序的主要技术:ASP.NET 与 ATL Server。每种框架都有一些特定的优缺点。在本部分,我将集中讲述如何用 ASP.NET 管理基于 Web 的 UI。下次我将集中讲述如何利用这两种框架来构建 Web 服务及其它功能。
  ASP.NET 究竟是什么?
  
  ASP.NET 是为处理 HTTP 请求而设计的类库。除了类库,ASP.NET 还包含几个管理请求的 IIS 组件。这些组件包括名为 ASPNET_ISAPI.DLL 的 ISAPI DLL 以及名为 ASPNET_WP.EXE 的辅助进程。ASP.NET 还在 IIS 中安装了新的映射,将 ASPX、ASCX、ASHX 和 ASMX 的文件请求重定向到 ASPNET_ISAPI.DLL。至此,ASPNET_ISAPI.DLL 将请求定向到 ASPNET_WP.EXE,在该进程中,ASP.NET 加载所需要的类来为请求提供服务。
  
  以名称为 HttpContext 的托管类为中心,ASP.NET 有一个很方便的对象模型。如果您曾经写过一个标准的 ISAPI DLL,那么您一定了解包含于 EXTENSION_CONTROL_BLOCK 中并传递给 ISAPI DLL 的 HttpExtensionProc 的信息。管理请求时,ISAPI DLL 对该结构进行检查,以获得诸如环境 ID、查询字符串,以及读写客户端的函数等信息。ASP.NET 将所有这些信息都包装在 HttpContext 类中。ASP.NET 还包括管理基于 Web 的 UI(通过 System.Web.UI.Page 类)以及管理 Web 服务(通过 System.Web.Services.WebService 类和 [WebMethod] 属性)的基本类结构。
  
  ASP.NET 是面向对象的。每个通过 ASP.NET 应用程序传递的请求都由名为 IHttpHandler 的类来处理,该类可以实现接口。这样就造就了一种扩展性很强的体系结构。您可以选择利用 ASP.NET 页体系结构或 Web 服务体系结构,或者,您还可以从头编写处理逻辑。图 1 显示了 ASP.NET 请求采取的路径。
  MIissues0311ASPColumnfig01
  
  图 2 基于 ATL Server 的请求的路径
  
  ATL Server 应用程序由许多 DLL(ISAPI 扩展和应用程序扩展)以及被称为 SRF(前面提到过)的 HTML 生成模板组成。这种体系结构很清楚地将应用程序表示和应用程序逻辑分离开来。网页的表示由包含 HTML 和特殊标记的 SRF 来定义。这些标记调用 ATL Server 应用程序 DLL。
  
  由于大多数 Web 应用程序的目标平台是 Windows,因此 ATL Server 应用程序要构建于 ISAPI DLL 之上。ATL Server 项目包含可处理粗略请求的单个 ISAPI 扩展 DLL。ATL Server 应用程序还包含用于多种精确请求处理的一个或多个应用程序 DLL。处理请求的类派生于 CRequestHandlerT,并且还包含您自己特有的、用来处理 SRF 中标记的代码。
  
  这些处理程序类包含将请求处理程序类和请求处理程序 DLL 关联起来以及将替代方法与 SRF 标记关联起来的字典。除了替代字典外,CRequestHandlerT 还包含访问标准 Web 应用程序元素的方法和成员变量,例如窗体变量、cookies、请求流以及响应流。
  
  当浏览器通过 HTTP 找到 .srf URL 时,IIS 知道用 ATL Server 应用程序的 ISAPI DLL 来打开站点。ATL Server 应用程序随后打开 SRF,并加载该应用程序的 DLL(如果它们还没有加载的话)。该应用程序随后将请求传送到默认的请求处理程序类,该类对 SRF 进行分析,以寻找有特殊记号的标记。每次在 SRF 中出现标记时,应用程序就调用存在于某应用程序 DLL 中某个处理程序类的替代方法。该替代方法动态生成浏览器的输出。图 2 显示了通过 ATL Server 应用程序的请求的路径。
  返回页首返回页首
  ATL Server 与 ASP .NET
  
  虽然 ATL Server 和 ASP.NET 都基于 ISAPI 体系结构,但是它们处理请求有很大不同。为了说明这些不同点,让我们看一个应用程序示例,该应用程序收集个人姓名和他(或她)的开发偏好。我将说明如何开发用户界面以及如何使用会话状态。在本专栏的下一部分,我将考察其他的一些功能(例如缓存和浏览器的能力),以及每种框架上 Web 服务的工作原理。图 3 对比了两种框架的一些功能。
  返回页首返回页首
  ASPX 文件与 SRF
  
  ASP.NET 和 ATL Server 为 ISAPI 体系结构引入了新的文件扩展名。ASP.NET 引入的文件类型有 ASPX、ASMX、ASCX 和 ASHX,还有一些其它类型。在 ASP.NET 框架中,这些文件类型中的每一种都有一个对应的托管类。对于 ASPX 文件来说,这样的类就是 System.Web.UI.Page。该 Page 类负责呈现基于 UI 的网页。图 4 显示了一个简单的 ASPX 文件。
  
  关于 ASPX 文件要注意的主要事项就是,网页顶端附近的继承指令以及按钮、标签和下拉列表标记的“runat=server”属性。这些标记表示了服务器端控件在 Visual Studio 中的代码隐藏文件中对应的类。
  
  相比之下,SRF 包含了最标准、最普通的 HTML 标记。ATL Server 没有服务器端组件体系结构。但是,它确实引入了服务器响应标记的概念。这些特殊的标记用双大括号 ({{}}) 表示。当 ATL Server 请求体系结构遇到一个服务器响应标记时,它期望在应用程序 DLL ÖÐ找到一个对应的处理程序函数。图 5 显示了一个简单的 SRF,它显示的用户界面与图 4 ASPX 示例中的用户界面大致相同。
  
  本文件中需要注意的最重要的事项是由双大括号括起来的特殊标记。例如,在 SRF 的顶端附近,您会看到指定应用程序默认处理程序的处理程序标记 ({{handler...}})。这会告诉 ATL Server 应用程序加载哪一个 DLL,以找到由响应标记调用的函数。其它的响应标记指出应用程序 DLL 中的入口点。
  返回页首返回页首
  “固有”对象
  
  ASP.NET 和 ATL Server 都包含有类似的固有请求和响应对象,这和典型的 ASP Ò»Ñù¡£在 ASP.NET 中,它们用 HttpRequest 和 HttpResponse 类来表示。在 ATL Server 中,它们用 CHttpRequest 和 CHttpResponse 类来表示。在每种框架中,它们的用途基本相同。请求对象封装了诸如请求参数和请求 URL 等项。响应对象包含有向客户端输出文本的功能。例如,为了向某个基于 ASP.NET 请求的输出流插入“Hello World”,只需要调用 Response.Write 即可,如下所示:
  
  protected void HelloWorld()
  {
   Response.Write("Hello World");
  }
  
  为了向基于 ATL Server 应用程序的客户端输出“Hello World”,使用 CHttpResponse 对象,如下所示:
  
  [tag_name(name="Hello") ]
  HTTP_CODE OnHello(void) {
   m_HttpResponse << "Hello World!";
   return HTTP_SUCCESS;
  }
  
  要注意如何利用图 5中的服务器响应标记来调用 OnHello 函数。(这个标记如下所示:Hello。)
  返回页首返回页首
  管理 UI 元素
  
  每种框架采用了不同的方法来管理 UI 元素。正如以前提到的那样,ASP.NET 中的 UI 支持围绕着服务器端控件模型。表示代码(ASPX 文件)利用“runat=server”属性声明了网页上的服务器端元素。只要在代码隐藏类中声明了相应的类,以编程方式访问控件就轻而易举了。例如,图 4中的代码说明了几种服务器端控件元素(例如,提交按钮、文本框元素,以及下拉列表)。代码隐藏页将 Button、TextBox 和 DropDownList 类声明为该页的成员,使得可以编程使用这些 UI 元素。为了找到 TextBoxName 元素中的数据,只需要访问 Text 属性即可,如下所示:
  
  String s = this.TextBoxName.Text;
  
  ASP.NET 服务器端控件还有自动跟踪视图状态的优点。当浏览器往返访问服务器时,UI 元素(如下拉列表框和单选按钮)会保持它们一致的状态。例如,最后一次在下拉列表框中选择的项就是显示的项。不需要编写任何特殊的代码来保证控件的行为正确。
  
  ATL Server 没有这样的控件模型。只能通过服务器响应标记来管理 UI。为了填充下拉列表,ATL Server 示例中用一个服务器响应函数来填充它(参见图 5中的{{ShowFeatureSelection}} 标记。图 6 说明了服务器响应函数是如何将各项插入到下拉列表的。
  
  ATL Server 与 ASP.NET 的方法不同,它不跟踪视图的状态。为了保持下拉列表的一致性,需要图 6中显示的代码。这些代码检查查询字符串传入的参数,并找出选择了哪一项。呈现代码确保用户选择的项在选项标记中包含“被选”属性。
  返回页首返回页首
  会话状态
  
  在 ASP.NET 中管理会话状态非常便利。ASP.NET 辅助进程处理低级的细节问题。当某个新客户端启动一个会话时,ASP.NET 将自动分配一个新会话对象 — 包含名称-值对的字典。System.Web.UI.Page 类包含一个目前客户会话信息的引用。访问客户的状态只需要利用索引器来访问会话字典即可。图 7 显示了创建新会话变量以及以后利用 ASP.NET 访问它们所需要的代码。
  
  在 ATL Server 中,管理会话状态稍微有点复杂。虽然利用 ATL Server 向导生成 ISAPI DLL 时包括一个会话管理器,但您仍需要编写代码来创建和访问会话对象。图 8 中的代码说明了如何在 ATL Server 中创建和访问会话变量。
  
  由 ATL Server 向导生成 ValidateAndExchange 函数。在每个请求的开始调用该方法,就像 ASP.NET Page 类中包含的 Init 与 Load 事件一样。ValidateAndExchange 为 ISAPI DLL 的会话管理器获得一个界面(通过 QueryService)。如果在标题中还没有会话 cookie,该方法就创建一个新会话,并为响应添加一个会话 cookie。如果这是现有会话的继续,这些代码就会利用会话信息来填充名称和年龄变量。注意,会话变量用 COM 变量表示。
  返回页首返回页首
  小结
  
  本月,我快速浏览了 ASP.NET 和 ATL Server。这些框架代表了当前处理 Windows 平台上 HTTP 请求的最先进的方法。每种框架都构建于久经测试的 ISAPI 体系结构之上,该体系结构几乎在十年前就已出现。ASP.NET 和 ATL Server 将它们的文件扩展名映射到特定的 DLL。ASP.NET DLL 就是 ASPNET_ISAPI.DLL。 ATL Server DLL 由 ATL Server 生成,但是对于它的大部分来说,它是可反复套用的代码。在这方面,ATL Server 的一个优点就是,实际上可以查阅(和更改)特殊应用程序的原始的 ISAPI 请求处理代码。
  
  虽然可以使用任何一种框架来编写大体上等同的应用程序,但这里需要折中考虑标准问题。通常,利用一种托管语言和 ASP.NET 框架来开发 ASP.NET 应用程序非常直接。但是,您会受该框架的支配(尽管 ASP.NET 利用其可扩展性已经缓和了灵活性问题)。另一方面,只要 ATL Server 应用程序通过了 IIS 的考验,它就包含了大多数 DLL µ÷ÓÃ — 一条高性能的建议。ATL Server 应用程序用 C++ 编写,因此您就拥有许多控制权和必要的责任。
  
  下一次我将对比 ASP.NET 与 ATL Server 的其它功能,包括缓冲状态、安全性和 Web 服务。
  图3到图8的链接:
  
  George Shepherd 专门从事 .NET Framework 软件的开发。他是 Programming with Microsoft Visual C++.NET (Microsoft Press, 2002) 的作者,并且还是 Applied .NET (Addison-Wesley,2001) 的合著者。他在研讨会上讲授 DevelopMentor,他还是一位在 Syncfusion 的 .NET 工具方面很有贡献的构架师。