Flask之run函数背后的秘密
2017-09-09 14:09
204 查看
一个最简单的基于Flask的web应用:
Flask版本为0.1
下面分析一下运行run()函数背后的细节:
Flask 的run方法如下:
Flask类的run方法调用werkzeug中的run_simple方法,默认情况下访问的是本机的5000端口。
use_reloader默认为False,调用内部的inner函数。
inner函数有两个功能:
1.调用make_server函数
这里使用默认的参数,指定handler和server的具体类型。
server是绑定的WSGIServer。handler绑定的是BaseRequestHandler,查看werkzeug.serving源码可以看到:
而WSGIRequestHandler是实现了WSGI转发的request handler
make_server的任务是返回一个WSGIServer服务器实例。
2.执行serve_forever方法,一直监听来自客户端的请求
WSGIServer的serve_forever实际是调用其父类class BaseServer的方法:
经过上面的分析,画出整个run函数背后的流程图如下:
Flask版本为0.1
from flask import Flask app = Flask(__name__) @app.route('/') def hello_world(): return 'Hello World!' if __name__ == '__main__': app.run()
下面分析一下运行run()函数背后的细节:
Flask 的run方法如下:
def run(self, host='localhost', port=5000, **options): # ...... from werkzeug import run_simple # ...... return run_simple(host, port, self, **options)
Flask类的run方法调用werkzeug中的run_simple方法,默认情况下访问的是本机的5000端口。
def run_simple(hostname, port, application, use_reloader=False, extra_files=None, threaded=False, processes=1): def inner(): srv = make_server(hostname, port, application, threaded, processes) try: srv.serve_forever() except KeyboardInterrupt: pass if use_reloader: #--- else: inner()
use_reloader默认为False,调用内部的inner函数。
inner函数有两个功能:
1.调用make_server函数
def make_server(host, port, app=None, threaded=False, processes=1): # .... else: handler = BaseRequestHandler server = WSGIServer srv = server((host, port), handler) srv.set_app(app) return srv
这里使用默认的参数,指定handler和server的具体类型。
server是绑定的WSGIServer。handler绑定的是BaseRequestHandler,查看werkzeug.serving源码可以看到:
BaseRequestHandler = WSGIRequestHandler,
而WSGIRequestHandler是实现了WSGI转发的request handler
make_server的任务是返回一个WSGIServer服务器实例。
from wsgiref.simple_server import WSGIServer class WSGIServer(HTTPServer): """BaseHTTPServer that implements the Python WSGI protocol""" WSGIServer是一种实现了WSGI协议的BaseHTTPServer,其继承自HTTPServer. 这里依赖的是wsgiref包。
2.执行serve_forever方法,一直监听来自客户端的请求
WSGIServer的serve_forever实际是调用其父类class BaseServer的方法:
def serve_forever(self, poll_interval=0.5): """Handle one request at a time until shutdown.""" # 处理客户端的请求,直到服务关闭 self.__is_shut_down.clear() try: while not self.__shutdown_request: r, w, e = _eintr_retry( select.select, [self], [], [], poll_interval) if self in r: self._handle_request_noblock() self.service_actions() finally: self.__shutdown_request = False self.__is_shut_down.set()
经过上面的分析,画出整个run函数背后的流程图如下:
相关文章推荐
- 【C++再学习】【07】自增自减操作符背后的秘密
- 隐藏在裸眼3D电视背后的秘密
- @Override标签背后的小秘密---记录java的思行合一(作者:leeon)
- 非常复杂,上双11数据大屏背后的秘密:大规模流式增量计算及应用
- 华山论剑之 C++引用的实现机制一(背后的秘密和真相)
- 电商Banner设计背后的12个人性的秘密
- 5.JavaScript优化及导航菜单背后的秘密
- 腾讯微信技术总监周颢:一亿用户增长背后的架构秘密
- 360特供机AK47“高配低价”背后的秘密:以牺牲用户体验为代价
- 表单提交Post方法、Get方法背后的秘密
- “叫好”与“叫座”背后的秘密
- 图解 | 芯片总动员之”齐刘海“背后的秘密
- Netflix赌赢《纸牌屋》背后的秘密武器:大数据分析
- ATL布幔下的秘密之虚函数背后的东西
- ATL布幔下的秘密之虚函数背后的东西
- 他们真的很厉害吗?破解超人背后的秘密
- @Override标签背后的小秘密---记录java的思行合一(作者:leeon)
- 腾讯微信技术总监周颢:一亿用户增长背后的架构秘密
- 腾讯微信技术总监周颢:一亿用户增长背后的架构秘密
- SpringBootApplication背后的秘密