003_00--http服务器从TCP连接中,按照http协议的格式读请求消息(tornado源码总结)
Posted on 2017-12-21 23:43 马顿 阅读(432) 评论(0) 编辑 收藏 举报模块名 | 接口类 | 模块功能 | 生成的数据结构 | 数据结构作用 | 处理数据的类 | 处理过程 |
web | Application | 1、构造request 2、调用对应函数生成response | tornado风格的request | request:包含了请求行、请求头部、请求数据的类 response:包含了状态行、响应头部、响应数据的类 | _RequestDispatcher(通过Application的工厂函数start_request获取) | 1、_RequestDispatcher.headers_received():构造request,将headers中各种数据写入request。从Application中找到url对应的handler。 2、_RequestDispatcher.data_received(chunk):保存请求数据的分段chunk 3、_RequestDispatcher.finish():将请求数据的分段chunks组合在一起,解析,然后写入request中 4、RequestHandler.execute(): 调用中间件,然后调用对应方法的处理函数 5、RequestHandler.flush() -> write_headers():将响应头部通过TCP连接返回值客户端 6、RequestHandler.flush() -> write(chunk):将响应数据通过TCP连接返回值客户端 |
tornado风格的response | RequestHandler | |||||
WSGIContainer | wsgi风格的environ | httputil.HTTPServerRequest | 1、WSGIContainer__call__():将tornado风格的request转换为wsgi风格的environ 2、WSGIContainer__call__():调用wsgi函数 3、wsgi函数调用中间件后,调用试图函数 4、wsgi函数调用start_response(status, response_headers)设置相应消息的状态行 5、wsgi函数的返回数据:WSGIContainer将其作为响应消息body保存 6、WSGIContainer.__call__() -> write_headers():将响应消息通过TCP连接返回客户端 | |||
wsgi风格的response | wsgi函数 | |||||
httpserver | HTTPServer | 1、从下层读取http请求消息 2、读取到消息后,区分上层是什么类型的应用,Application还是WSGIContainer。调用对应接口处理数据 | HTTP1ServerConnection(在handle_stream内生成) | 1、HTTP1Connection:创建一个该类,用于从TCP连接中读取http数据 2、_ServerRequestAdapter:创建一个该类,用于提供给HTTP1Connection,作为本层的处理http数据的类 3、创建一个循环,不断从TCP连接中读取http数据 | ||
_ServerRequestAdapter(通过HTTPServer的工厂函数start_request获取) | 如果部署的是Application: 1、headers_received():调用_RequestDispatcher.headers_received()。 2、data_received():上调用_RequestDispatcher.data_received()。 3、finish():调用 _RequestDispatcher.finish()。 | |||||
如果部署的是WSGIContainer: 1、headers_received():在本层将headers转换成tornado风格的request。 2、data_received():在本层保存请求数据分段chunk。 3、finish():在本层将请求数据的分段chunks组合在一起,解析,然后写入request中,之后调用 WSGIContainer.__call__()。 | ||||||
http1connection | HTTP1Connection | 1、从TCP连接中读取http请求消息的请求行 2、从TCP连接中读取http请求消息的请求头部 3、从TCP连接中读取http请求消息的请求数据 | tornado风格的start_line | 代表请求行 | HTTP1Connection | 1、header_data = stream.read_until_regex(b"\r?\n\r?\n") 从IOSteam中异步读取请求行+请求头部,这两部分与请求数据通过两个回车换行分隔 2、start_line, headers = _parse_headers(header_data) 从数据中解析出start_line 和 headers 3、HTTP1Connection._read_body()根据headers中对请求数据的描述,读取请求数据。请求数据可能较长,回分段到达,每到达一段都调用上层的delegate.data_received(chunk) 4、delegate.finish()当请求数据读取完毕后,通知上层http请求消息读取完毕 |
tornado风格的headers | 代表请求头部 | |||||
tornado风格的chunks | 请求数据可能较大,会分段到达,每到达一段都保存在chunks中,当全部到达都,再做解析 |
tornado数据从TCP到wsgi函数的四个模块的主要功能:
http1connection:从TCP连接中,按照http协议请求消息/响应消息的格式,读取http消息,并且将http消息解析为python类:start_line, headers, body
将 start_line, headers, body组织成http响应消息写回至客户端
httpserver:保存所有的来自客户端的TCP连接
为所有TCP连接维持一个死循环,不断从TCP连接中读取http请求消息,将下层生成的start_line, headers, body组织成request
调用上层的模块(wsgi APP)处理request
WSGIContainer:将适用于tornado application的request类转换成适用于WSGI应用的environ
按照wsgi协议的格式,调用wsgi 函数。
将返回的数据组织成 start_line, headers, body(tornado用于描述响应数据三部分的类)
调用 http1connection对应方法将响应数据写回至客户端
WSGI函数:调用各种中间件,然后调用试图函数处理请求
调用start_response回掉函数,返回状态行、响应头部
返回body部分
tornado数据从TCP到tornado Application的四个模块的主要功能:
http1connection:同上
httpserver:保存所有的来自客户端的TCP连接
为所有TCP连接维持一个死循环,不断从TCP连接中读取http请求消息,将下层生成的start_line, headers, body传递给Application处理
Application:将start_line, headers, body转换成request类
找到处理该请求消息url的RequestHandler
调用RequestHandler对应的方法处理request
RequestHandler: 处理request,生成start_line, headers, body (RequestHandler提供各种方法去写这三部分,可参考对应文章)
调用 http1connection对应方法将响应数据写回至客户端
可以在利用各层的特性,实现不同的需求。