深入解析Asp.NET架构

添加人:yeemio零级(94分)   添加时间:2007-08-31    阅读次数:3942  收藏此教程
MSDN的WEBCAST,感觉单纯看一遍意义不大,做个笔记,以备不时只需查找方便。代码部分本人在XP+VS2005+SQL2005测试通过,不过我是初学,请大家指教。

首先我们来说一下Asp.net工作原理。
具体描述下这样的:首先客户请求WEB页。然后WEB服务寻找指令文件(.aspx),而这时就是aspnet_isapi.dll这个动态连接库来处理。接着Asp.net代码被发送到公共语言运行时进行编译。接着HTML流返回给浏览器和令。最后由浏览器处理HTML并显示页面。
什么是ISAPI呢?
在Internet时代的开端,客户端的需求非常有限;.htm文件就可以满足他们的需求。但是,随着时间的流逝,客户端需求的扩充超越了.htm文件或静态文件所包含的功能。
开发者需要扩充或扩展Web服务器的功能。Web服务器厂商设计了不同的解决方案,但是都遵循同一个主题“向Web服务器插入某些组件”。所有的Web服务器补充技术都允许开发者建立并插入组件以增强Web服务器的功能。微软公司提出了ISAPI(Internet服务器API),网景公司提出了NSAPI(网景服务器API)等等。ISAPI是一种重要的技术,它允许我们增强与ISAPI兼容的Web服务器(IIS就是一种与ISAPI兼容的Web服务器)的能力。我们使用下面的组件达到这个目的:
1,ISAPI扩展:ISAPI扩展是使用Win32动态链接库来实现的。你可以把ISAPI扩展看作是一个普通的应用程序。ISAPI扩展的处理目标是http请求。
2,ISAPI过滤器:客户端每次向服务器发出请求的时候,请求要经过过滤器。客户端不需要在请求中指定过滤器,只需要简单地把请求发送给Web服务器,接着Web服务器把请求传递给相关的过滤器。接下来过滤器可能修改请求,执行某些登录操作等等。
ASP.NET请求的处理过程:
ASP.NET请求处理过程是基于管道模型的,在模型中ASP.NET把http请求传递给管道中的所有模块。每个模块都接收http请求并有完全控制权限。模块可以用任何自认为适合的方式来处理请求。一旦请求经过了所有HTTP模块,就最终被HTTP处理程序处理。HTTP处理程序对请求进行一些处理,并且结果将再次经过管道中HTTP模块。
ISAPI的筛选器:
IIS本身是不支持动态页面的,也就是说它仅仅支持静态html页面的内容,对于如.asp,.aspx,.cgi,.php等,IIS并不会处理这些标记,它就会把它当作文本,丝毫不做处理发送到客户端。为了解决这个问题。IIS有一种机制,叫做ISAPI的筛选器,它是一个标准组件(COM组件)。
Asp.net服务在注册到IIS的时候,会把每个扩展可以处理的文件扩展名注册到IIS里面(如:*.ascx、*.aspx等)。扩展启动后,就根据定义好的方式来处理IIS所不能处理的文件,然后把控制权跳转到专门处理代码的进程中让这个进程开始处理代码,生成标准的HTML代码,生成后把这些代码加入到原有的Html中,最后把完整的Html返回给IIS,IIS再把内容发送到客户端。
HttpModule:
HttpModule实现了ISAPI Filter的功能,是通过对IhttpModule接口的继承来处理。
HTTP模块是实现了System.Web.IhttpModule接口的.NET组件。这些组件通过在某些事件中注册自身,把自己插入ASP.NET请求处理管道。当这些事件发生的时候,ASP.NET调用对请求有兴趣的HTTP模块,这样该模块就能处理请求了。
HttpModule的实现:
1. 编写一个类,实现IhttpModule接口。
2. 实现Init 方法,并且注册需要的方法。
3. 实现注册的方法。
4. 实现Dispose方法,如果需要手工为类做一些清除工作,可以添加Dispose方法的实现,但这不是必需的,通常可以不为Dispose方法添加任何代码。
5. 在Web.config文件中,注册您编写的类。
下边我们来看例子,HttpModule的实现:
首先添加一个类库,然后在引用里引用System.Web和System.Security这两个命名空间。然后写个类,代码如下:

 1using System;
 2using System.Collections.Generic;
 3using System.Text;
 4using System.Web;
 5using System.Security.Principal;
 6namespace Httplibrary
 7{
 8    public class SecurityModules : IHttpModule
 9    {
10        public void Init(HttpApplication r_objApplication)
11        {
12            // 向Application 对象注册事件处理程序,核心部分。
13            r_objApplication.AuthenticateRequest += new EventHandler(this.AuthenticateRequest);
14        }

15        public void Dispose()
16        {
17
18        }

19        private void AuthenticateRequest(object r_objSender, EventArgs r_objEventArgs)
20        {
21            // 鉴别用户的凭证,并找出用户角色。
22            HttpApplication objApp = (HttpApplication)r_objSender;
23            HttpContext objContext = (HttpContext)objApp.Context;
24            if ((objApp.Request["userid"] == null) || (objApp.Request["password"] == null))
25            {
26                objContext.Response.Write("用户名和密码为空,验证失败!");
27                objContext.Response.End();
28            }

29            string userid = "";
30            userid = objApp.Request["userid"].ToString();
31            string password = "";
32            password = objApp.Request["password"].ToString();
33            string[] strRoles;
34            strRoles = AuthenticateAndGetRoles(userid, password);
35            if ((strRoles == null) || (strRoles.GetLength(0) == 0))
36            {
37                objContext.Response.Write("用户名或密码错误!");
38                objApp.CompleteRequest();//终止一个Http请求
39
40            }

41            GenericIdentity objIdentity = new GenericIdentity(userid, "CustomAuthentication");
42            objContext.User = new GenericPrincipal(objIdentity, strRoles);
43        }

44        private string[] AuthenticateAndGetRoles(string r_strUserID, string r_strPassword)
45        {
46            string[] strRoles = null;
47            if ((r_strUserID.Equals("Zhangsan")) && (r_strPassword.Equals("111")))
48            {
49                strRoles = new String[1];
50                strRoles[0] = "Administrator";
51            }

52            else if ((r_strUserID.Equals("Lisi")) && (r_strPassword.Equals("222")))
53            {
54                strRoles = new string[1];
55                strRoles[0] = "User";
56            }

57            return strRoles;
58        }

59    }

60}

  

编译一下,下边做测试页面,很简单,放一个label,text=“测试页面”如果成功则显示测试页面。然后在web.config里面配置,这里很重要。添加 注意注释部分。

<httpModules>
      <!--注意我这里的Httplibrary是你添加引用的那个DLL的文件名.Httplibrary.SecurityModules
      中前边部分是你那个类的名称空间,后边的是你建的类的名字。-->
      <add name=" Test1 " type="Httplibrary.SecurityModules,Httplibrary"/>
</httpModules>

然后添加  这个节点,这个大家应该都能明白。
<authorization>
      <deny users="?"/>
 </authorization>
然后启动测试页面。刚启动开始后页面一定显示“用户名和密码为空,验证失败!”呵呵,别忘记了咱们这就是目的,然后在你的地址栏后边添加?userid=Zhangsan&password=111这行字。然后就会显示“测试页面”这几个字。大家可以多输入几个名字单步调试一下就明白了。

WebConfig设置
<httpModules>
<add type=“classname,assemblyname”
name=“modulename”/>
<remove name=“modulename”/>
<clear/>
</httpModules>
子标记说明:
<add>将HttpModule 类添加到应用程序。请注意,如果以前已指定了相同的谓词/路径组合(例如在父目录的Web.config 文件中),则对的第二个调用将重写以前的设置。
<remove>从应用程序移除HttpModule 类。
<clear>从应用程序移除所有HttpModule 映射。
深入研究HttpModule
HttpModule通过对HttpApplication对象的一系列事件的处理来对HTTP处理管道施加影响,这些事件在HttpModule的Init方法中进行注册,包括:
BeginRequest
AuthenticateRequest
AuthorizeRequest
ResolveRequestCache
AcquireRequestState
PreRequestHandlerExecute
PostRequestHandlerExecute
ReleaseRequestState
UpdateRequestCache
EndRequest
我们都可以对以上事件进行重新定义,注意时重新定义不时覆盖。我们看一个例子,多个HttpModule的实现,建立两个类库,什么都相同就是类名不相同,引入相应的命名空间后我们编写这个类,代码如下:

 
3页 第1上一页123下一页
相关的教程: ASP.NET
收藏此教程

当前平均分: 0.0(2 次打分)

-5-4-3-2-1012345
评论主题
您的大名
您的评论
验证码 点击换一个验证码
知识库搜索: