Django源码剖析
一、Django底层剖析之一次请求到响应的整个流程
As we all know,所有的Web应用,其本质上其实就是一个socket服务端,而用户的浏览器就是一个socket客户端
#!/usr/bin/env python
#coding:utf-8 import socket def handle_request(client):
buf = client.recv(1024)
client.send("HTTP/1.1 200 OK\r\n\r\n")
client.send("Hello, Seven") def main():
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.bind(('localhost',8000))
sock.listen(5) while True:
connection, address = sock.accept()
handle_request(connection)
connection.close() if __name__ == '__main__':
main()
上述代码使用socket实现了其本质,对于所有的python web程序来说,一般会分为两部分:服务器程序和应用程序。服务器程序负责对socket服务器进行封装,并在请求到来时,对请求的数据进行整理。应用程序则负责具体的逻辑处理。为了方便应用程序的开发,避免大家重复的造轮子,因此有人发明了相关的工具——Web框架,for example:Django、Flask、web.py and so on。不同的框架可能采用不同的目录结构,但是无论如何,开发出的应用程序都要和服务器程序配合,才能为用户提供服务。以前,如何选择合适的Web应用程序框架成为困扰Python初学者的一个问题,这是因为,一般而言,Web应用框架的选择将限制可用的Web服务器的选择,反之亦然。那时的Python应用程序通常是为CGI,FastCGI,mod_python中的一个而设计,甚至是为特定Web服务器的自定义的API接口而设计的。
PythonWeb服务器网关接口(Python Web Server Gateway Interface,缩写为WSGI)是Python应用程序或框架和Web服务器之间的一种接口,已经被广泛接受, 它已基本达成它的可移植性方面的目标。
概述:
Django的请求到响应的流程,简单的来说就是利用wsgi,当用户发来一个request进行response,响应前发送request_started信号,经过中间件的process_request,响应完成后会调用中间件的process_response。
1.浏览器端用户用url发来了一个请求
当django程序启动时,会根据settings中:
源码截图:

(注:这里是project名.wsgi.application,博主创建的project名为s3。)
执行applicaion对应的函数:
源码截图:

接下来我们来看get_wsgi_application函数:
源码截图:

从上述源码可看出django每次请求响应都会返回一个WSGIHandler类的实例。
WSGIHandler类源码截图:

这里,我们需要关注的是:
load_middleware只有第一次请求会调用,即中间件的加载只会在第一次请求时执行。
WSGIhandler类中发送了request_started信号。
下来我们首先关注一下他的父类base.BaseHandler类:
base.BaseHandler类源码截图:

中间件的完整执行流程图:

备注:由上图可看出:
- 当请求到来时,会首先经过中间件的Process_Request,如果Process_Request有return即当前url没有通过中间件,则程序直接跳转到最后一个Process_Response,然后逆序执行所有的Process_Response。
- 然后程序会进入url,这时程序会检测用户有没有设置process_view,如果有,则接下来先执行process_view,如果process_view有return,则程序直接跳转到最后一个Process_Response,然后逆序执行所有的Process_Response。
- 如果上一步没有process_view,程序会执行views文件中的函数
- 执行完上一步,程序会检测有没有异常出现,如果有,则先执行中间件类对应的process_exception
- 最后,程序会逆序执行所有的Process_Response。
备注:request_middleware、view_middleware 是顺序执行,template_response_middleware、response_middleware、exception_middleware 是逆序执行。
url:
首先程序会根据配置文件中:
源码截图:

找到urls.py文件
url匹配源码:

这里直接使用当前url是否属于LocaleRegexURLResolver这个类。
LocaleRegexURLResolver类:
预编译:

正则匹配:
我们需要关注的是LocaleRegexURLResolver类的resolve方法:

注:self.url_patterns是所有的正则url,这里对正则url进行循环;new_path是用户输入的url,这里pattern.resolve是执行RegexURLPattern类的resolve方法:

由上述源码可看出RegexURLPattern类的resolve方法即通过regex.search进行具体的匹配操作,其中regex封装了re模块。
我们定义的url:
示例代码:
from django.conf.urls import url
from django.contrib import admin
from APP01 import views
urlpatterns = [
url(r'^admin/', admin.site.urls),
url(r'^articles/(?P<year>[0-9]{4})/$', views.special_case_2003),
url(r'^articles/([0-9]{4})/$', views.year_archive),
url(r'^articles/([0-9]{4})/([0-9]{2})/$', views.month_archive),
url(r'^articles/([0-9]{4})/([0-9]{2})/([0-9]+)/$', views.article_detail),
]
源码url截图:

从上述源码中可看出url方法接收正则表达式和view两个参数,最终返回一个RegexURLPattern对象,RegexURLPattern类对正则表达式和view做进一步处理

由上述源码可看出,在完成正则匹配后,view会被作为回调函数运行。由此解释了url是如何与views函数进行绑定的。
接下来,程序调用views函数,并对模板进行渲染,并返回到view,程序如果没有异常,执行中间件的Process_Response(详见上文中间件的执行流程),最终程序发送一个信号 request_finished信号,订阅这个信号的事件会清空并释放任何使用中的资源。
Django源码剖析的更多相关文章
- Django 源码小剖: 初探 WSGI
Django 源码小剖: 初探 WSGI python 作为一种脚本语言, 已经逐渐大量用于 web 后台开发中, 而基于 python 的 web 应用程序框架也越来越多, Bottle, Djan ...
- Django Rest Framework源码剖析(八)-----视图与路由
一.简介 django rest framework 给我们带来了很多组件,除了认证.权限.序列化...其中一个重要组件就是视图,一般视图是和路由配合使用,这种方式给我们提供了更灵活的使用方法,对于使 ...
- Django Rest Framework源码剖析(七)-----分页
一.简介 分页对于大多数网站来说是必不可少的,那你使用restful架构时候,你可以从后台获取数据,在前端利用利用框架或自定义分页,这是一种解决方案.当然django rest framework提供 ...
- Django Rest Framework源码剖析(六)-----序列化(serializers)
一.简介 django rest framework 中的序列化组件,可以说是其核心组件,也是我们平时使用最多的组件,它不仅仅有序列化功能,更提供了数据验证的功能(与django中的form类似). ...
- Django Rest Framework源码剖析(五)-----解析器
一.简介 解析器顾名思义就是对请求体进行解析.为什么要有解析器?原因很简单,当后台和前端进行交互的时候数据类型不一定都是表单数据或者json,当然也有其他类型的数据格式,比如xml,所以需要解析这类数 ...
- Django Rest Framework源码剖析(四)-----API版本
一.简介 在我们给外部提供的API中,可会存在多个版本,不同的版本可能对应的功能不同,所以这时候版本使用就显得尤为重要,django rest framework也为我们提供了多种版本使用方法. 二. ...
- Django Rest Framework源码剖析(三)-----频率控制
一.简介 承接上篇文章Django Rest Framework源码剖析(二)-----权限,当服务的接口被频繁调用,导致资源紧张怎么办呢?当然或许有很多解决办法,比如:负载均衡.提高服务器配置.通过 ...
- Django Rest Framework源码剖析(二)-----权限
一.简介 在上一篇博客中已经介绍了django rest framework 对于认证的源码流程,以及实现过程,当用户经过认证之后下一步就是涉及到权限的问题.比如订单的业务只能VIP才能查看,所以这时 ...
- 跨站请求伪造(csrf),django的settings源码剖析,django的auth模块
目录 一.跨站请求伪造(csrf) 1. 什么是csrf 2. 钓鱼网站原理 3. 如何解决csrf (1)思路: (2)实现方法 (3)实现的具体代码 3. csrf相关的装饰器 (1)csrf_p ...
随机推荐
- Spring MVC可参数化的视图控制器
以下示例显示如何使用Spring Web MVC框架来实现多动作控制器的可参数化视图控制器.可参数化视图允许将请求映射到网页. 所下所示配置 - import javax.servlet.http.H ...
- jsp a href怎么传参数?
jsp中超链接传值使用键值对格式,多个键值对之间用&分隔,即<a href="show.jsp?name=tom&pass=123&score=78,5&quo ...
- WPF-数据转换
有时我们展现的数据,需要进行转换,比如如果一个学生的成绩过了60,我们显示一个Pass的图片. XAML: <Window x:Class="DeepXAML.MainWindow&q ...
- Codeforces Beta Round #25 (Div. 2)--A. IQ test
IQ test time limit per test 2 seconds memory limit per test 256 megabytes input standard input outpu ...
- Python 使用MySQL
在导入MySQLdb之前,需要安装MySQLdb模块.使用pip安装,命令如下: pip install MySQL-python 安装成功后,导入MySQLdb模块 import MySQLdb 连 ...
- 【BZOJ4810】[Ynoi2017]由乃的玉米田 bitset+莫队
[BZOJ4810][Ynoi2017]由乃的玉米田 Description 由乃在自己的农田边散步,她突然发现田里的一排玉米非常的不美.这排玉米一共有N株,它们的高度参差不齐.由乃认为玉米田不美,所 ...
- stochastic matrix
w Stochastic matrix - Wikipedia https://en.wikipedia.org/wiki/Stochastic_matrix Suppose you have a ...
- java javassis crack class
java javassis crack class java 反编译 android 反编译 1. jad http://varaneckas.com/jad/jad158e.linux.inte ...
- <2013 07 29> 游泳
7月12日,在巴塞罗那的海滩学会用狗刨式游泳. 7月14日,在尼斯-戛纳海滩继续练习,稍式蛙泳仰泳. 7月28日,在慕尼黑某湖边吃烧烤,下湖练习. 7月29日,在慕尼黑奥林匹克游泳馆学会了仰泳,稍试自 ...
- VSpy之C Code Interface的使用
Spy3 要运行 CCodeInterface 功能,需要安装运行环境,建议安装 Visual Studio2003,2005,2008,2010 或更新的版本.当然也可以安装 VC express ...