day 65 crm(2) admin源码解析,以及简单的仿造admin组件
前情提要:
crm中的admin组件重写.
一:admin的autodiscover
作用:实现扫面该项目中的所有的admin
1:执行顺序->
按照注册的顺序执行
二:单例模式
1:普通案例的格式
该案例的内存地址不同,实例对象有自己的实例空间,
2:单例模式的应用
单例模式的内存地址相同,在python文件加载过程中.单例模式可以减少相同文件的缓存,
2>1 基于__new__的单例模式
2>2 基于模块的单例模式
python中特有的,模块导入多次只会实现一次
2>2>1基于上例子
新建一个文件,并创建一个类,
2>2>2 导入该报重命名
内存地址相同,即是单例模式,只要是同一个程序就是单例
三:注册功能
1: admin中应用单例模式
2:site.register的注册功能
2>1:在register源码中
class AdminSite方法__init__内创建了一个空字典,存放单例的内容
register方法中存放入口参数,model 和admin_class
其中
如果 admin_class =None
1 or 0 1
2 or 3 2
0 or 1 1
如果有值,则走admin_calss 即自定制, 如果没有值则,ModelAdmin
modelAdmin 为默认配置类
当注册时在字典中增加key,valuse
2>2 如果全部注册完了以后,可以尝试打印该字典
如只注册了3个
则会显示5个,因为系统自动注册了两个,auto 和group
启动下看看:::
2 >3 register方法
该方法 会循环的从字典中拿取key和values ,
key为model 即为表明
valuse为样式类,如果不填写则传入默认的
四:设置url APPEND_SLASH参数
默认效果
五:url的分发
1 :url中的分发
django自带的以调用属性的方式,显示,使用为使用了@properp ,使方法以属性的形式可以代用
2:样式:
path('路由/',([
path('text01/',text01),
path('text02/',text02),
],None,None))
3:运行顺序
4:效果:
5:url 路由的多级分发
就是把原视图方法的地方在进行一次路由分发
5>1 : 运行路线
5>2 :效果图
六:从新设计admin的url分发
1:设置url的分发
在原视图函数的位置上设置一个可执行函数,返回值为视图函数,或者视图函数分层
2:动态的为模型类创建增删改查url
2>1 通过刚才字典的进行进一步操作
3: 拿到注册的字典,进行操作
循环的从字典内拿出来 key 和values
注意:valuse 的值是分为 配置类,和默认配置类
4:给temp增加path路径
4>1:参照admin表的模式.
自定义明/app名字/表明/操作名
4>2: 通过model的模型类获取app名字和model(表名)
4:2>1 获取表名
4:2>2 获取app名
5: 最终一级效果图
:效果图:
六:二层分发:(固定增删改查)
1: 在一层分发后面再开一个分发函数,get_urls2()
2:函数内部,
增删改查,4个path
注意什么都不写,即默认为点开一层的效果,我们这里让他为查询界面
七:自己设计一个stark组件(自己写一个admin)
1:创建一个新的app :stark
2:把app注册到setting中
3:把启动命令加入到apps中
from django.apps import AppConfig
from django.utils.module_loading import autodiscover_modules #django中源码的扫描包 class StarkConfig(AppConfig):
name = 'stark'
def ready(self):
autodiscover_modules('stark') #注册扫描
# print("adasd")
扫描每个注册的app
4:编写注册函数
4>1:默认样式类
5:注册实例
6: 配置路由
7:路由视图函数做了什么
7>1: 因为路由层调用了urls . 进入urls函数,urls 函数继续调用get_urls函数
7>2:get_urls 函数说明
该函数实现了动态为模型创建增删改查的url的一层分发
一层分发根据表名而定
从注册内容中拿取字典
其中:model 是注册的表名对象
config_obj是 注册的样式对象
temp.append(
path("%s/%s/" % (app_label, model_name), config_obj.get_urls)
)
实现当前层的以及分发
效果图:
之后的
config_obj.get_urls 实现二级分发
8:二级分发固定为增删改查
8>1: 解释参数意思
8>2 :django作者把二层分发写在了默认配置类中
这样可以直接在调用配置类的时候,就可以实现二层分发
class ModelStark(object):
'''
默认配置类
'''
list_display = ("__str__",) def __init__(self, model):
self.model = model def list_view(self, request):
# print(self) # 当前访问模型表对应的配置类对象
# print(self.model) # 当前访问模型表 data = self.model.objects.all()
print(data)
print("-------",self.list_display)
data_list=[]
dict1={}
for obj in data:
lis =[]
for msg in self.list_display:
lis.append(getattr(obj,msg))
# print("kkkkkkk",lis)
data_list.append(lis)
print("jjjjjjjjj",data_list)
return render(request, 'stark/list_view.html', {
"data_list":data_list,
"list_display":self.list_display }) def add_view(self, request):
return HttpResponse("add_view") def change_view(self, request, id):
return HttpResponse("change_view") def delete_view(self, request, id):
return HttpResponse("delete_view") @property
def get_urls(self):
temp = [
path("", self.list_view),
path("add/", self.add_view),
path("(\d+)/change/", self.change_view),
path("(\d+)/delete/", self.delete_view),
] return (temp, None, None)
8>3: 二级分发中的get_ursl 解析
注意:当 '这什么都没写!!!!!!' 的时候,即进入一层分发的界面,这里走的是list_view视图 8:>4 默认配置类的解释
这个model 在注册时候传入.方便数据操作
8>5 :默认配置中的样式
这里的默认配置类只设置的返回"__str__" 即类名
注意!!!!
这里的是('__str__',) 是个元祖!!!
8>5>1
解析4个增删改查
!!!!!!!!!!!!查:
结果:
前端书写
效果:
增,删,改暂时没写
所有代码!!
表目录
staites 表
# -*- coding: utf- -*-
# @Time : // :
# @Author : Endless-cloud
# @Site :
# @File : stites.py
# @Software: PyCharm
'''
┏┓ ┏┓+ +
┏┛┻━━━┛┻┓ + +
┃ ┃
┃ ━ ┃ ++ + + +
████━████ ┃+
┃ ┃ +
┃ ┻ ┃
┃ ┃ + +
┗━┓ ┏━┛
┃ ┃
┃ ┃ + + + +
┃ ┃ Code is far away from bug with the animal protecting
┃ ┃ + 神兽保佑,代码无bug
┃ ┃
┃ ┃ +
┃ ┗━━━┓ + +
┃ ┣┓
┃ ┏┛
┗┓┓┏━┳┓┏┛ + + + +
┃┫┫ ┃┫┫
┗┻┛ ┗┻┛+ + + +
''' from django.urls import path
from django.shortcuts import HttpResponse,render
from app01.models import * class ModelStark(object):
'''
默认配置类
'''
list_display = ("__str__",)
def __init__(self, model):
self.model = model
def list_view(self, request):
# print(self) # 当前访问模型表对应的配置类对象
# print(self.model) # 当前访问模型表 data = self.model.objects.all()
print(data)
print("-------",self.list_display)
data_list=[]
dict1={}
for obj in data:
lis =[]
for msg in self.list_display:
lis.append(getattr(obj,msg))
data_list.append(lis)
print("jjjjjjjjj",data_list)
return render(request, 'stark/list_view.html', {
"data_list":data_list,
"list_display":self.list_display
})
def add_view(self, request):
return HttpResponse("add_view") def change_view(self, request, id):
return HttpResponse("change_view") def delete_view(self, request, id):
return HttpResponse("delete_view") @property
def get_urls(self):
temp = [
path("", self.list_view),
path("add/", self.add_view),
path("(\d+)/change/", self.change_view),
path("(\d+)/delete/", self.delete_view),
] return (temp, None, None) class StarkSite:
'''
stark全局类
''' def __init__(self):
self._registry = {} def register(self, model, admin_class=None, **options):
admin_class = admin_class or ModelStark
self._registry[model] = admin_class(model) def get_urls(self):
# 动态为注册的模型类创建增删改查URL
temp = []
# {Book:ModelAdmin(Book),Publish:ModelAdmin(Publish)}
for model, config_obj in self._registry.items():
print("---->", model, config_obj)
model_name = model._meta.model_name
app_label = model._meta.app_label
temp.append(
path("%s/%s/" % (app_label, model_name), config_obj.get_urls)
) '''
path("stark/app01/book",self.list_view)
path("stark/app01/book/add",self.add_view)
path("stark/app01/publish",self.list_view)
path("stark/app01/publish/add",self.add_view) ''' return temp @property
def urls(self):
return self.get_urls(), None, None site = StarkSite()
models 表
from django.db import models # Create your models here.
class Book(models.Model):
title = models.CharField(max_length=)
price = models.DecimalField(max_digits=, decimal_places=)
pubdate = models.DateField()
publish = models.ForeignKey('Publish', on_delete=models.CASCADE, null=True)
authors = models.ManyToManyField('Author')
state = models.IntegerField(choices=[(, "已出版"), (, "未出版社")], default=) #映射,设置默认值
def __str__(self):
return self.title class Publish(models.Model):
name = models.CharField(max_length=)
city = models.CharField(max_length=)
email = models.EmailField() def __str__(self):
return self.name
class Author(models.Model):
name =models.CharField(max_length=)
age =models.IntegerField()
au_detail =models.OneToOneField('AuthorDetail',on_delete=models.CASCADE)
def __str__(self):
return self.name
class AuthorDetail(models.Model):
tel = models.CharField(max_length=)
addr = models.CharField(max_length=)
birthday = models.DateField()
stark表
# -*- coding: utf- -*-
# @Time : // :
# @Author : Endless-cloud
# @Site :
# @File : stark.py
# @Software: PyCharm
'''
┏┓ ┏┓+ +
┏┛┻━━━┛┻┓ + +
┃ ┃
┃ ━ ┃ ++ + + +
████━████ ┃+
┃ ┃ +
┃ ┻ ┃
┃ ┃ + +
┗━┓ ┏━┛
┃ ┃
┃ ┃ + + + +
┃ ┃ Code is far away from bug with the animal protecting
┃ ┃ + 神兽保佑,代码无bug
┃ ┃
┃ ┃ +
┃ ┗━━━┓ + +
┃ ┣┓
┃ ┏┛
┗┓┓┏━┳┓┏┛ + + + +
┃┫┫ ┃┫┫
┗┻┛ ┗┻┛+ + + +
''' # print("")
from stark.service.stites import site,ModelStark
from .models import * class BookConfig(ModelStark):
list_display=["title","price"] class PublishConfig(ModelStark):
list_display=["name","city"]
site.register(Book,BookConfig)
site.register(Publish)
print(site._registry)
list_view.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<!-- 最新版本的 Bootstrap 核心 CSS 文件 -->
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap@3.3.7/dist/css/bootstrap.min.css" integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous">
</head>
<body>
<h3>查看数据</h3> <table>
<tbody>
<tr>
{% for obj in list_display %}
<th>
{{obj}}
</th>
{% endfor %}
</tr>
{% for msg in data_list %}
<tr>
{% for foo in msg %}
<td>
{{foo}}
</td>
{% endfor %}
</tr>
{% endfor %} </tbody>
</table> <table border="">
<tr>
<td>asd</td>
<td>ads</td>
<td>asd</td>
<td>asd</td>
</tr>
</table>
</body>
</html>
day 65 crm(2) admin源码解析,以及简单的仿造admin组件的更多相关文章
- django之admin源码解析
解析admin的源码 第一步:项目启动,加载settings文件中的 INSTALLED_APPS 里边有几个app就加载几个,按照注册顺序来执行. 第二步:其中加载的是admin.py,加载每一个a ...
- admin源码解析以及仿照admin设计stark组件
---恢复内容开始--- admin源码解析 一 启动:每个APP下的apps.py文件中. 首先执行每个APP下的admin.py 文件. def autodiscover(): autodisco ...
- django -admin 源码解析
admin源码解析 单例模式 单例模式(Singleton Pattern)是一种常用的软件设计模式,该模式的主要目的是确保某一个类只有一个实例存在.当你希望在整个系统中,某个类只能出现一个实例时,单 ...
- admin源码解析及自定义stark组件
admin源码解析 单例模式 单例模式(Singleton Pattern)是一种常用的软件设计模式,该模式的主要目的是确保某一个类只有一个实例存在.当你希望在整个系统中,某个类只能出现一个实例时,单 ...
- abp vnext2.0之核心组件模块加载系统源码解析与简单应用
abp vnext是abp官方在abp的基础之上构建的微服务架构,说实话,看完核心组件源码的时候,很兴奋,整个框架将组件化的细想运用的很好,真的超级解耦.老版整个框架依赖Castle的问题,vnext ...
- Spring源码解析-AOP简单分析
AOP称为面向切面编程,在程序开发中主要用来解决一些系统层面上的问题,比如日志,事务,权限等等,不需要去修改业务相关的代码. 对于这部分内容,同样采用一个简单的例子和源码来说明. 接口 public ...
- 【Spring源码解析】—— 简单工厂模式的BeanFactory的超简版实现
一.什么是简单工厂模式 设计模式的核心是“分工”,通过分工将对象与职责划分的更细化,进而提升系统设计的可扩展性,使其更容易维护. 开闭原则:对扩展开放,对修改关闭:要增加一个新的处理逻辑,可以开一个新 ...
- HashMap源码解析(简单易懂)
/* 每一个key-value存储在Node<K,V>中,HashMap由Node<K,V>[]数 组组成. */ static class Node<K,V> i ...
- 6 admin(注册设计)源码解析、单例模式
1.单例模式 https://www.cnblogs.com/yuanchenqi/articles/8323452.html 单例模式(Singleton Pattern)是一种常用的软件设计模式, ...
随机推荐
- aspx导出文件
System.IO.StringWriter sw = new System.IO.StringWriter(); HtmlTextWriter htw = new HtmlTextWriter(sw ...
- Mybatis传值为空需要配置JdbcType来解决吗?(XML文件不需要配置JdbcType)
1,解决思路,配置自定义的语言驱动,重写自己的Paramethander package cn.com.servyou.gxdqy.tool.xmlhelper; import org.apache. ...
- Notepad++ 中如何将代码格式化
Notepad++ 中如何将代码格式化 在阅读别人的代码时偶尔会遇到格式很乱,阅读起来很费劲的情况,若手动改,很容易出错且很费时间,这时可以借助一些专业的编辑器来格式化代码,NotePad++是一 ...
- Jsp+servlet+mysql搭建套路
1.建立数据库根据需求建立相应的数据库确立数据库的字段.属性.主键等2.建立javaweb项目,搭建开发环境在开发环境的/WebRoot/WEB-INF下建立lib文件夹,存放需要使用的jar包常用的 ...
- UVa 11280 Flying to Fredericton (DP + Dijkstra)
题意:给出n(2<=n<=100)个城市之间的m(0<=m<=1000)条航线以及对应的机票价格,要求回答一些询问,每个询问是给出最大停留次数S,求从其实城市Calgary到终 ...
- The serializable class XXX does not declare a static final serialVersionUID field of type long
问题: 在Eclipse中,继承类时,总是提示下面的警告(Warning),按理说警告是没有关系的,但是程序看起来老不爽了,这是强迫症的关系(呵呵) The serializable class XX ...
- i9-9900k烤机
新装机一台,记录烤机参数 硬件配置: cpu: i9-9900k 主板:技嘉Z390 AORUS PRO WIFI 内存:海盗船ddr4 3200 显卡:技嘉gtx1080ti 硬盘:三星970Pro ...
- 如何更新world文档的目录
在想要设置目录的文档页,右键 -> 更新域, 或者在想要设置目录的文档页,按下 F9 即可 拓展: 在目录文档页 ,按Ctrl 并且单击鼠标可以跟踪目标连接 如果内容对您有所帮助,请打赏--- ...
- How Many Tables HDOJ
How Many Tables Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)T ...
- javascript data format
Date.prototype.Format = function(fmt) { var o = { "M+" : this.getMonth()+1, //月份 "d+& ...