一、admin的源码流程

首先可以确定的是:路由关系一定对应一个视图函数

a、当点击运行的时候,会先找到每一个app中的admin.py文件,并执行

b、执行urls.py

admin.site是什么?

admin.site,urls    返回的是一个元组,里面的第一个元素是一个列表

django-admin的源码流程
我们自己生成的动态的访问url
====================================初级版=========================
from django.shortcuts import HttpResponse
from django.conf.urls import url
from django.contrib import admin
from app01 import views
def login(request):
return HttpResponse("ok") url_list = [] for model_class,v in admin.site._registry.items():
print(model_class) #打印的是每一个类<class 'app01.models.UserInfo'>
cls_name = model_class._meta.model_name #当前类名称的小写
app_name = model_class._meta.app_label #当前app的名称
val = url(r'^{0}/{1}/$'.format(app_name,cls_name), login, name="login")
url_list.append(val) urlpatterns = [
url(r'^admin/', admin.site.urls),
# admin.site这个对象里面有一个属性_registry = {}
#点击urls查看源码返回的是一个元组,元组的第一个元素是一个列表
url(r'^index/', ([
url(r'^app01/userinfo/$', login,name="login"),
url(r'^app01/roles/$', login,name="login"),
],None,None)), url(r'^index2/', (url_list,None,None,)), #吧上面定义的列表拿下来,这是后就动态生成了
]
================================升级============================
路径http://127.0.0.1:8001/index/app01/roles/后面还有增删改查的路径
http://127.0.0.1:8001/index/app01/roles/add/
http://127.0.0.1:8001/index/app01/roles/1/change/
http://127.0.0.1:8001/index/app01/roles/1/del/ 实现流程
from django.shortcuts import HttpResponse
from django.conf.urls import url
from django.contrib import admin
from app01 import views
def login(request):
return HttpResponse("ok") def change_list(request):
return HttpResponse("列表页面") def add_view(request):
return HttpResponse("添加页面") def change_view(request,nid):
return HttpResponse("修改页面") def delete_view(request,nid):
return HttpResponse("删除页面") url_list = [] for model_class,v in admin.site._registry.items():
print(model_class) #打印的是每一个类<class 'app01.models.UserInfo'>
cls_name = model_class._meta.model_name #当前类名称的小写
app_name = model_class._meta.app_label #当前app的名称
urls_list = url(r'^{0}/{1}/$'.format(app_name,cls_name), change_list, name="login")
url_list.append(urls_list) add_url = url(r'^{0}/{1}/add/$'.format(app_name, cls_name), add_view, name="login")
url_list.append(add_url) change_url = url(r'^{0}/{1}/(\d+)/change/$'.format(app_name, cls_name), change_view, name="login")
url_list.append(change_url) del_url = url(r'^{0}/{1}/(\d+)/del/$'.format(app_name, cls_name), delete_view, name="login")
url_list.append(del_url) urlpatterns = [
url(r'^admin/', admin.site.urls),
# admin.site这个对象里面有一个属性_registry = {}
#点击urls查看源码返回的是一个元组,元组的第一个元素是一个列表
url(r'^index/', (
[
url(r'^app01/userinfo/$', login,name="login"),
url(r'^app01/roles/$', login,name="login"),
],None,None)),
url(r'^index2/', (url_list,None,None,)), #吧上面定义的列表拿下来,这是后就动态生成了
] 说明了:
url的本质:它读取_registry所有字典里面的数据,为字典里面的每一个类生成了4个url
==================================修改上面的版本=============================
定义了一个
def get_urls():
temp = [
url(r'^$'.format(app_name, cls_name), change_list),
url(r'^add/$'.format(app_name, cls_name), add_view),
url(r'^del/$'.format(app_name, cls_name), delete_view),
url(r'^change/$'.format(app_name, cls_name), change_view)
]
return temp url_list = []
for model_class,v in admin.site._registry.items():
print('-------',model_class) #打印的是每一个类<class 'app01.models.UserInfo'>
cls_name = model_class._meta.model_name #当前类名称的小写
app_name = model_class._meta.app_label #当前app的名称
方式一:
# all_urls = url(r'^{0}/{1}/'.format(app_name,cls_name), (get_urls(),None,None,))
方式二:
all_urls = url(r'^{0}/{1}/'.format(app_name,cls_name), include(get_urls()) )
url_list.append(all_urls) urlpatterns = [
url(r'^admin/', admin.site.urls),
# admin.site这个对象里面有一个属性_registry = {}
#点击urls查看源码返回的是一个元组,元组的第一个元素是一个列表
url(r'^index/', (
[
url(r'^app01/userinfo/', ([
url(r'^$', change_list, name="login"),
url(r'^add/$', add_view, name="login"),
url(r'^(\d+)/del/$', delete_view, name="login"),
url(r'^(\d+)/change/$', change_view, name="login"),
],None,None),name="login"),
url(r'^app01/usertype/', ([
url(r'^$', change_list, name="login"),
url(r'^add/$', add_view, name="login"),
url(r'^(\d+)/del/$', delete_view, name="login"),
url(r'^(\d+)/change/$', change_view, name="login"),
], None, None), name="login"),],None,None)),
url(r'^app02/article/', ([
url(r'^$', change_list, name="login"),
url(r'^add/$', add_view, name="login"),
url(r'^(\d+)/del/$', delete_view, name="login"),
url(r'^(\d+)/change/$', change_view, name="login"),
],None,None),name="login"), # index和index2的两个是一样的,我们可以用index2的方式替代index
url(r'^index2/', (url_list,None,None,)), #吧上面定义的列表拿下来,这是后就动态生成了
] include的本质就是:返回了一个元组,元组的第一个是这个模块
include里面
既可以写一个列表include([]),利用include做分发
也可以返回一个字符串:帮我们去找到这个模块,找到所有的映射关系 include(model_admin.urls)
model_admin是什么?ModelAdmin对象的urls

总结

- admin源码流程
a. 运行程序,找到每一个app中的 admin.py 文件,并加载
- app01.admin.py
- 创建admin.site中的对象
- 执行对象的 register方法,目的:将注册类添加到 _registry中
_registry = {
key是传进来的model value:是ModelAdmin的对象,传了两个参数
models.Role: ModelAdmin(models.Role,admin.site),
models.UserInfo: ModelAdmin(models.UserInfo,admin.site)
models.UserType: ModelAdmin(models.UserType,admin.site)
} - app02.admin.py
- 用app01.admin中创建那个admin.site对象
- 执行对象的 register方法,目的:讲注册类添加到 _registry中
_registry = {
models.Role: ModelAdmin(models.Role,admin.site),
models.UserInfo: ModelAdmin(models.UserInfo,admin.site)
models.UserType: ModelAdmin(models.UserType,admin.site)
models.Article: ModelAdmin(models.Article,admin.site)
} admin.site是一个对象(单例模式创建),其中封装了:
_registry = {
models.Role: ModelAdmin(models.Role,admin.site),
models.UserInfo: ModelAdmin(models.UserInfo,admin.site)
models.UserType: ModelAdmin(models.UserType,admin.site)
models.Article: ModelAdmin(models.Article,admin.site)
}
b. urls.py
再次调用 admin.site 对象的 urls属性:
urlpatterns = [
url(r'^admin/', admin.site.urls),
] class ModelAdmin(object):
def __init__(self,model_class,site):
self.model_class = model_class
self.site = site def changelist_view(self,request):
data_list = self.model_class.objects.all() #是动态的
return HttpResponse('列表页面') def add_view(self,request):
return HttpResponse('添加页面') def delete_view(self,request,nid):
return HttpResponse('删除页面') def change_view(self,request,nid):
return HttpResponse('修改页面') def get_urls(self):
urlpatterns = [
url(r'^$', self.changelist_view),
url(r'^add/$', self.add_view),
url(r'^(.+)/delete/$', self.delete_view),
url(r'^(.+)/change/$', self.change_view),
]
return urlpatterns @property
def urls(self):
return self.get_urls() class AdminSite(object):
def __init__(self):
self._registry = {} def register(self,model_class,model_admin):
self._registry[model_class] = model_admin(model_class,self) def get_urls(self):
"""
models.Role: ModelAdmin(models.Role,admin.site),
models.UserInfo: ModelAdmin(models.UserInfo,admin.site)
models.UserType: ModelAdmin(models.UserType,admin.site)
models.Article: ModelAdmin(models.Article,admin.site)
"""
url_list = []
for model_class,model_admin in self._registry.items():
model_class是一个类
app_name = model_class._meta.app_label
model_name = model_class._meta.model_name
url_list += [
url('%s/%s' %(app_name,model_name,), include(model_admin.urls))
] return url_list @property
def urls(self):
return (self.get_urls(), None,None )

django-admin的源码流程的更多相关文章

  1. Django admin组件源码流程

    admin 组件 Django 自带的用户后台组件 用于用户便携的操作 admin 组件核心 启动 注册 设计url 启动核心代码 每个app 通过 apps.py 扫描 admin.py 文件 并执 ...

  2. Django rest_framework 认证源码流程

    一.请求到来后,都要先执行dispatch方法 dispatch根据请求方式的不同触发get/post/put/delete等方法 注意,APIView中的dispatch方法有很多的功能 def d ...

  3. Django Rest Framework框架源码流程

    在详细说django-rest-framework源码流程之前,先要知道什么是RESTFUL.REST API . RESTFUL是所有Web应用都应该遵守的架构设计指导原则. REST是Repres ...

  4. Django session 源码流程

    流程 Django session源码流程 首先执行的是SessionMiddleware的init方法 import_module(settings.SESSION_ENGINE) 导入了一个 dj ...

  5. Django drf:序列化增删改查、局部与全局钩子源码流程、认证源码分析、执行流程

    一.序列化类的增.删.改.查 用drf的序列化组件   -定义一个类继承class BookSerializer(serializers.Serializer):   -写字段,如果不指定source ...

  6. Django rest framework源码分析(4)----版本

    版本 新建一个工程Myproject和一个app名为api (1)api/models.py from django.db import models class UserInfo(models.Mo ...

  7. Django rest framework源码分析(1)----认证

    目录 Django rest framework(1)----认证 Django rest framework(2)----权限 Django rest framework(3)----节流 Djan ...

  8. Django rest framework源码分析(2)----权限

    目录 Django rest framework(1)----认证 Django rest framework(2)----权限 Django rest framework(3)----节流 Djan ...

  9. Django REST framework 源码剖析

    前言 Django REST framework is a powerful and flexible toolkit for building Web APIs. 本文由浅入深的引入Django R ...

随机推荐

  1. 第26月第13天 hibernate导包

    1. https://yq.aliyun.com/ziliao/386827

  2. windows上git安装

    Git的官方网站:http://git-scm.com 1.下载:http://msysgit.github.com/ 2.安装 3.配置 用户名.邮箱 这个很重要将来项目提交的账号   $ git ...

  3. ES6 基础

    转载自:ES6 基础 一.新的变量声明方式 let/const 与var不同,新的变量声明方式带来了一些不一样的特性,其中最重要的两个特性就是提供了块级作用域与不再具备变量提升. 通过2个简单的例子来 ...

  4. day 8 - 1 文件操作

    文件操作 注意: 1. r+ 最为常用 2.encoding 的编码格式一定要与文件编码格式一致 读取 r  rb #在本地创建 txt 格式的文件默认使用 gbk 格式 f = open('e:/p ...

  5. mysql 原理 ~ kill session解析

    一 简介:kill session为什么需要很久 二 kill语句分为三类  1 DML语句   2 select语句   3 DDL语句 三  kill都要做什么操作   1 kill对sessio ...

  6. Python问题:'Nonetype' object is not iterable

    参考链接:http://blog.csdn.net/dataspark/article/details/9953225 [解析] 这个错误提示一般发生在将None赋给多个值时. [案例] 定义了如下的 ...

  7. P3168 [CQOI2015]任务查询系统

    题目地址:P3168 [CQOI2015]任务查询系统 主席树的模板题 更模板的在这儿:P3834 [模板]可持久化线段树 1(主席树) 形象的说,P3834是"单点修改,区间查询" ...

  8. Pytorch tutorial 之Transfer Learning

    引自官方:  Transfer Learning tutorial Ng在Deeplearning.ai中讲过迁移学习适用于任务A.B有相同输入.任务B比任务A有更少的数据.A任务的低级特征有助于任务 ...

  9. Boost多线程编程

    Boost多线程编程   背景 •       今天互联网应用服务程序普遍使用多线程来提高与多客户链接时的效率:为了达到最大的吞吐量,事务服务器在单独的线程上运行服务程序: GUI应用程序将那些费时, ...

  10. windows命令行获取时间

    在写Windows批处理脚本时,常常需要获取系统日期.时间戳记,用作文件名.文件夹名.log等等. 本文介绍了如何获取自订的系统日期.时间戳记. 首先,在Windows中,系统日期由以下参数获得: % ...