您好,欢迎访问三七文档
HTTP协议的结构2004-11-0809:18:54我来说两句收藏我要投稿Internet是由各个协议连接起来的,而我们现在使用最广的莫过于HTTP协议了,也就是超文本传输协议,与FTP(文件传输协议)不同,由于主要用于超文本传输,因此HTTP协议显得更简单一点。今天我们来介绍一下HTTP协议的基本格式。在这里,我们所谈及的HTTP协议以HTTP/1.1为标准,并且使用NetVampirePro4.0来取得与HTTP服务器的通信Log,您也可以使用其它的HTTP下载工具来取得通信Log。在HTTP协议中,服务端是指提供HTTP服务的部分,客户端是指你使用的浏览器或者下载工具等等。在通讯时,由客户端发出请求连接,服务端建立连接;然后,客户端发出HTTP请求(Request),服务端返回响应信息(Respond),由此完成一个HTTP操作。我们来通过一个例子来了解这个过程:(以下是NetVampire进行的一次连接,以下红色字体为作者添加)P01-5-2616:10:43Connectingtogo2.163.com...//连接服务器P01-5-2616:10:44Connectedtogo2.163.com[61.129.65.148]//解析IP地址,以下为HTTP操作S01-5-2616:10:44GET/~minift/epretty/pretty.zipHTTP/1.1//请求行(RequestLine),表示使用GET方式取得文件,使用HTTP/1.1协议//以下为请求头部(RequestHead)S01-5-2616:10:44Connection:close//表示非持续性连接S01-5-2616:10:44Host:go2.163.com//主机名称S01-5-2616:10:44Accept:*/*//接受的数据类型S01-5-2616:10:44Pragma:no-cache//参数(与以前的服务器兼容)S01-5-2616:10:44Cache-Control:no-cache//不使用缓存S01-5-2616:10:44Referer:~minift/epretty//从该网址转来S01-5-2616:10:44User-Agent:Mozilla/4.04[en](Win95;I;Nav)//客户端标识S01-5-2616:10:44Cookie:AdId=ACDDAAAAAAAS01-5-2616:10:44//以下为RespondR01-5-2616:10:47HTTP/1.0200OK//响应行(RespondLine),服务器使用HTTP/1.0协议,状态值(StatusCode)为200,状态为OK,表示文件可以读取R01-5-2616:10:47Date:Sat,26May200108:15:54GMT//现在的时间,用格林威治时间表示R01-5-2616:10:47Server:Apache/1.3.14(Unix)mod_layout/2.9.9//服务器类型R01-5-2616:10:47Last-Modified:Fri,04May200102:42:56GMT//文件最后更新时间R01-5-2616:10:47ETag:e614cf-37965-3af21730R01-5-2616:10:47Accept-Ranges:bytes//接受的范围单位R01-5-2616:10:47Content-Length:227685//文件长度R01-5-2616:10:47Content-Type:application/zip//MIME类型R01-5-2616:10:47X-Cache:MISSfromshca8R01-5-2616:10:47X-Cache-Lookup:MISSfromshca8:80R01-5-2616:10:47Connection:close//表示文件传输完毕就关闭连接。R01-5-2616:10:47//以下为文件传输P01-5-2616:10:47Datatransferstarted下面来讲解使用的格式(LRCF=@13@10,即回车,SP=SPACE,即空格)Request:协议方式SP文件URISP协议版本LRCF(请求行)(以下为头部)头部类型:头部值LRCF头部类型:头部值LRCF头部类型:头部值LRCF......LRCF表示头部结束(如果有体部,以下为体部)Respond:协议版本SP状态值SP状态描述LRCF(响应行)(以下为头部)头部类型:头部值LRCF头部类型:头部值LRCF头部类型:头部值LRCF......LRCF表示头部结束(如果有体部,以下为体部)由上可见,请求与相应的格式只有部分不同,是很容易理解的,现在你应该基本了解HTTP协议了吧,也能看懂那些通信Log了吧,下一次我们讲专门讲解在响应行中的状态值含义及一些特殊情况。3.1如何调用HTTP模块2013-03-2712:03陶辉机械工业出版社字号:T|T《深入理解Nginx:模块开发与架构解析》第3章开发一个简单的HTTP模块,本章讲述了如何开发一个基本的HTTP模块,这里除了获取请求的包体外没有涉及异步处理问题。本节为大家介绍。AD:51CTO学院:IT精品课程在线看!第二部分如何编写HTTP模块本部分内容第3章开发一个简单的HTTP模块第4章配置、error日志和请求上下文第5章访问第三方服务第6章开发一个简单的HTTP过滤模块第7章Nginx提供的高级数据结构第3章开发一个简单的HTTP模块当通过开发HTTP模块来实现产品功能时,是可以完全享用Nginx的优秀设计所带来的、与官方模块相同的高并发特性的。不过,如何开发一个充满异步调用、无阻塞的HTTP模块呢?首先,需要把程序嵌入到Nginx中,也就是说,最终编译出的二进制程序Nginx要包含我们的代码(见3.3节);其次,这个全新的HTTP模块要能介入到HTTP请求的处理流程中(具体参见3.1节、3.4节、3.5节)。满足上述两个前提后,我们的模块才能开始处理HTTP请求,但在开始处理请求前还需要先了解一些Nginx框架定义的数据结构(见3.2节),这是后面必须要用到的;正式处理请求时,还要可以获得Nginx框架接收、解析后的用户请求信息(见3.6节);业务执行完毕后,则要考虑发送响应给用户(见3.7节),包括将磁盘中的文件以HTTP包体的形式发送给用户(见3.8节)。本章最后会讨论如何用C++语言来编写HTTP模块,这虽然不是Nginx官方倡导的方式,但C++向前兼容C语言,使用C++语言开发的模块还是可以很容易地嵌入到Nginx中。本章不会深入探讨HTTP模块与Nginx的各个核心模块是如何配合工作的,而且这部分提到的每个接口将只涉及用法而不涉及实现原理,在第3部分我们才会进一步阐述本章提到的许多接口是如何实现异步访问的。3.1如何调用HTTP模块在开发HTTP模块前,首先需要了解典型的HTTP模块是如何介入Nginx处理用户请求流程的。图3-1是一个简化的时序图,这里省略了许多异步调用,忽略了多个不同的HTTP处理阶段,仅标识了在一个典型请求的处理过程中主要模块被调用的流程,以此帮助读者理解HTTP模块如何处理用户请求。完整的流程将在第11章中详细介绍。从图3-1中看到,worker进程会在一个for循环语句里反复调用事件模块检测网络事件。当事件模块检测到某个客户端发起的TCP请求时(接收到SYN包),将会为它建立TCP连接,成功建立连接后根据nginx.conf文件中的配置会交由HTTP框架处理。HTTP框架会试图接收完整的HTTP头部,并在接收到完整的HTTP头部后将请求分发到具体的HTTP模块中处理。这种分发策略是多样化的,其中最常见的是根据请求的URI和nginx.conf里location配置项的匹配度来决定如何分发(本章的例子正是应用这种分发策略,在第10章中会介绍其他分发策略)。HTTP模块在处理请求的结束时,大多会向客户端发送响应,此时会自动地依次调用所有的HTTP过滤模块,每个过滤模块可以根据配置文件决定自己的行为。例如,gzip过滤模块根据配置文件中的gzipon|off来决定是否压缩响应。HTTP处理模块在返回时会将控制权交还给HTTP框架,如果在返回前设置了subrequest,那么HTTP框架还会继续异步地调用适合的HTTP模块处理子请求。开发HTTP模块时,首先要注意的就是HTTP框架到具体的HTTP模块间数据流的传递,以及开发的HTTP模块如何与诸多的过滤模块协同工作(第10章、第11章会详细介绍HTTP框架)。下面正式进入HTTP模块的开发环节。【责任编辑:b《深入理解Nginx:模块开发与架构解析》第3章开发一个简单的HTTP模块,本章讲述了如何开发一个基本的HTTP模块,这里除了获取请求的包体外没有涉及异步处理问题。本节为大家介绍定义自己的HTTP模块。3.4HTTP模块的数据结构(1)定义HTTP模块方式很简单,例如:1.ngx_module_tngx_http_mytest_module;其中,ngx_module_t是一个Nginx模块的数据结构(详见8.2节)。下面来分析一下Nginx模块中所有的成员,如下所示:1.typedefstructngx_module_sngx_module_t;2.structngx_module_s{3./*下面的ctx_index、index、spare0、spare1、spare2、spare3、version变量不需要在定义时赋值,可以用Nginx准备好的宏NGX_MODULE_V1来定义,它已经定义好了这7个值。4.#defineNGX_MODULE_V10,0,0,0,0,0,15.6.对于一类模块(由下面的type成员决定类别)而言,ctx_index表示当前模块在这类模块中的序号。这个成员常常是由管理这类模块的一个Nginx核心模块设置的,对于所有的HTTP模块而言,ctx_index是由核心模块ngx_http_module设置的。ctx_index非常重要,Nginx的模块化设计非常依赖于各个模块的顺序,它们既用于表达优先级,也用于表明每个模块的位置,借以帮助Nginx框架快速获得某个模块的数据(HTTP框架设置ctx_index的过程参见10.7节)*/7.ngx_uint_tctx_index;8.9./*index表示当前模块在ngx_modules数组中的序号。注意,ctx_index表示的是当前模块在一类模块中的序号,而index表示当前模块在所有模块中的序号,它同样关键。Nginx启动时会根据ngx_modules数组设置各模块的index值。例如:10.ngx_max_module=0;11.for(i=0;ngx_modules[i];i++){12.ngx_modules[i]-index=ngx_max_module++;13.}14.*/15.ngx_uint_tindex;16.17.//spare系列的保留变量,暂未使用18.ngx_uint_tspare0;19.ngx_uint_tspare1;20.ngx_uint_tspare2;21.ngx_uint_tspare3;22.//模块的版本,便于将来的扩展。目前只有一种,默认为123.ngx_uint_tversion;24.25./*ctx用于指向一类模块的上下文结构体,为什么需要ctx呢?因为前面说过,Nginx模块有许多种类,不同类模块之间的功能差别很大。例如,事件类型的模块主要处理I/O事件相关的功能,HTTP类型的模块主要处理HTTP应用层的功能。这样,每个模块都有了自己的特性,而ctx将会指向特定类型模块的公共接口。例如,在HTTP模块中,ctx需要指向ngx_http_module_t结构体*/26.void*ctx;27.28.//commands将处理nginx
本文标题:HTTP协议的结构
链接地址:https://www.777doc.com/doc-2876491 .html