django源码分析pythonmanage.pyrunserver

django源码分析pythonmanage.pyrunserver
django是⼀个快速开发web应⽤的框架,笔者也在django框架上开发不少web应⽤,闲来⽆事,就想探究⼀下django底层到底是如何实现的,本⽂记录了笔者对django源码的分析过程
I believe to become a better developer you MUST get a better understanding of the underlying software systems you use on a
daily basis and that includes programming languages, compilers and interpreters, databases and operating systems, web
servers and web frameworks. And, to get a better and deeper understanding of those systems you MUST re-build them from scratch, brick by brick, wall by wall.
笔者摘抄了⼀段话,送给阅读本⽂的读者
正⽂
如何分析django源码,笔者选择从django项⽬的启动⽅式开始 python manage.py runserver,本⽂主要分析了django项⽬的启动流程
#!/usr/bin/env python
import os
import sys
if__name__ == "__main__":
人脸识别巡更系统try:
anagement import execute_from_command_line
except ImportError:
# The above import may fail for some other reason. Ensure that the
# issue is really that Django is missing to avoid masking other
# exceptions on Python 2.
try:
import django
except ImportError:
raise ImportError(
"Couldn't import Django. Are you sure it's installed and "
"available on your PYTHONPATH environment variable? Did you "
"forget to activate a virtual environment?"
)
raise
execute_from_command_line(sys.argv)
在manage.py⽂件中,我们看到启动⽂件的⼊⼝是 excute_from_command_line(sys.argv)
def execute_from_command_line(argv=None):
"""
A simple method that runs a ManagementUtility.
"""
utility = ManagementUtility(argv)
这个函数是将命令⾏参数传递给了ManagementUtility类,这个类的execute⽅法负责执⾏,这个⽅法主要是⼀些django的初始化参数的检查,以及通过sys.argv获取命令,得到相应的命令后,执⾏命令。
execute⽅法中的部分代码
...
figured:
# Start the auto-reloading dev server even if the code is broken.
# The hardcoded condition is a code smell but we can't rely on a
# flag on the command class because we haven't located it yet.
if subcommand == 'runserver'and'--noreload'not in self.argv:
try:
autoreload.check_errors(django.setup)()
except Exception:
# The exception will be raised later in the child process
# started by the autoreloader. Pretend it didn't happen by
# loading an empty list of applications.
apps.all_models = defaultdict(OrderedDict)
ofp002
apps.app_configs = OrderedDict()
apps.apps_ready = dels_ready = ady = True
...
execute⽅法中有⼀段代码autoreload.check_errors(django.setup)(),会对django项⽬进⾏⼀些必要的初始化,并检查初始化的错误django.setup()⽅法会注册项⽬app和配置⽇志⽂件,注册app即对settings.INSTALLED_APPS中的app进⾏导⼊,并执⾏⼀些初始化⽅法进⾏完所有初始化动作,继续执⾏代码
execute⽅法中的部分代码
...
elif self.argv[1:] in (['--help'], ['-h']):
sys.stdout.write(self.main_help_text() + '\n')
else:
self.fetch_command(subcommand).run_from_argv(self.argv)
...
self.fetch_command(subcommand)会返回⼀个BaseCommand类,主要是分析subcommand参数(subcommand是sys.argv⾥⾯获取到的),导⼊相应的命令类,最后返回类
我们通过分析,runserver参数最终获取到的命令类是django/contrib/staticfiles/management/command/runserver.py ⾥的Command类
这是Command类的继承关系图。Command类通过run_from_argv(self.argv)执⾏命令
BaseCommand类中run_from_argv⽅法的部分代码
...
try:
except Exception as e:
aceback or not isinstance(e, CommandError):
raise
...
run_from_argv(self.argv)⽅法中主要通过execute()来继续执⾏,excute中会对django项⽬进⾏检查,然后通过self.handle()继续执⾏RunserverCommand类⾥⾯的handle⽅法部分代码
def handle(self, *args, **options):
  ...
  if not self.addr:
self.addr = '::1'if self.use_ipv6 else'127.0.0.1'
熏蒸桶self._raw_ipv6 = self.use_ipv6
self.run(**options)
handle()⽅法⾥⾯也进⾏了⼀些检查,然后继续执⾏self.run()来启动服务器
RunserverCommand中的部分代码
def run(self, **options):
"""
Runs the server, using the autoreloader if needed
"""
电子倾斜仪use_reloader = options['use_reloader']
if use_reloader:
autoreload.main(self.inner_run, None, options)
else:防水伸缩缝
self.inner_run(None, **options)
def inner_run(self, *args, **options):
...
try:
handler = _handler(*args, **options)
run(self.addr, int(self.port), handler,
ipv6=self.use_ipv6, threading=threading, server_cls=self.server_cls)
as e:
.
..
run⽅法中选择了启动的解释器,最后都是通过inner_run中的run⽅法来执⾏,会启动⼀个WSGIServer, WSGIServer需要⼀个回调函数
handler(或者application),来执⾏django视图⾥⾯代码。
⾄此,django项⽬服务器启动流程完毕,启动了⼀个简单的WSGIServer,开始接受请求,解析请求参数,将请求参数传递给回调函数handler(或者application,django框架的核⼼内容),handler根据参数执⾏相应的代码,返回数据给WSGIServer,WSGIServer最终将数据返回给浏览器。
关于wsgi可以参考这篇⽂章,
抑制的生活
总结:
我认为django启动流程中对于我们开发者最重要的⼀步在于django.setup(),⾥⾯做了很多初始化的⼯作,包括导⼊各个app的models,运⾏各个app的run函数,配置⽇志⽂件。我们如果想要在项⽬的启动的时候做⼀些我们⾃⼰的初始化动作,可以选择在这个地⽅下⼿。

本文发布于:2024-09-24 17:16:08,感谢您对本站的认可!

本文链接:https://www.17tex.com/tex/3/104864.html

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。

标签:启动   请求   笔者
留言与评论(共有 0 条评论)
   
验证码:
Copyright ©2019-2024 Comsenz Inc.Powered by © 易纺专利技术学习网 豫ICP备2022007602号 豫公网安备41160202000603 站长QQ:729038198 关于我们 投诉建议