[Django 0-1] Apps模块

Apps 源码分析

Apps 下主要有两个类: AppConfigApps.

目录结构

apps/                      # 应用目录
├── __init__.py            # 应用初始化文件
├── config.py              # AppConfig 类
├── registry.py            # Apps 类

AppConfig

位于 apps/config.py 文件中, 主要用来定义应用的配置信息和初始化过后的过程函数。

属性

  • name: 应用的名称, 一般是应用的包名.
  • module: 应用的模块, 一般是应用的 __init__.py 文件.
  • apps: 应用管理器, 用来管理应用的注册和配置信息.
  • label: 应用的标签, 包名的最后一部分, 如django.contrib.admin => admin.
  • verbose_name: 应用的显示名称, 一般是应用的名称的首字母大写形式.
  • path: 应用的路径, 一般是应用的包路径.
  • models_module: 应用的模型模块, 通过import_models加载,在 app 初始化完成前,该属性为None.
  • models: 应用的模型 mapping[str, models.Model], 通过import_models加载,在 app 初始化完成前,该属性为None.

重要函数

  • create(): 类方法,返回一个AppConfig实例,通过外部的 entry 字符串,加载目录下的 apps 中的子类并初始化返回,可以通过设置default属性来控制实例化哪个AppConfig子类。

class AppConfig:...@classmethoddef create(cls, entry):"""Factory that creates an app config from an entry in INSTALLED_APPS."""# create() eventually returns app_config_class(app_name, app_module).app_config_class = Noneapp_name = Noneapp_module = None# If import_module succeeds, entry points to the app module.try:app_module = import_module(entry)except Exception:passelse:# If app_module has an apps submodule that defines a single# AppConfig subclass, use it automatically.# To prevent this, an AppConfig subclass can declare a class# variable default = False.# If the apps module defines more than one AppConfig subclass,# the default one can declare default = True.if module_has_submodule(app_module, APPS_MODULE_NAME):mod_path = "%s.%s" % (entry, APPS_MODULE_NAME)mod = import_module(mod_path)# Check if there's exactly one AppConfig candidate,# excluding those that explicitly define default = False.app_configs = [(name, candidate)for name, candidate in inspect.getmembers(mod, inspect.isclass)if (issubclass(candidate, cls)and candidate is not clsand getattr(candidate, "default", True))]if len(app_configs) == 1:app_config_class = app_configs[0][1]else:# Check if there's exactly one AppConfig subclass,# among those that explicitly define default = True.app_configs = [(name, candidate)for name, candidate in app_configsif getattr(candidate, "default", False)]if len(app_configs) > 1:candidates = [repr(name) for name, _ in app_configs]raise RuntimeError("%r declares more than one default AppConfig: ""%s." % (mod_path, ", ".join(candidates)))elif len(app_configs) == 1:app_config_class = app_configs[0][1]# Use the default app config class if we didn't find anything.if app_config_class is None:app_config_class = clsapp_name = entry# If import_string succeeds, entry is an app config class.if app_config_class is None:try:app_config_class = import_string(entry)except Exception:pass# If both import_module and import_string failed, it means that entry# doesn't have a valid value.if app_module is None and app_config_class is None:# If the last component of entry starts with an uppercase letter,# then it was likely intended to be an app config class; if not,# an app module. Provide a nice error message in both cases.mod_path, _, cls_name = entry.rpartition(".")if mod_path and cls_name[0].isupper():# We could simply re-trigger the string import exception, but# we're going the extra mile and providing a better error# message for typos in INSTALLED_APPS.# This may raise ImportError, which is the best exception# possible if the module at mod_path cannot be imported.mod = import_module(mod_path)candidates = [repr(name)for name, candidate in inspect.getmembers(mod, inspect.isclass)if issubclass(candidate, cls) and candidate is not cls]msg = "Module '%s' does not contain a '%s' class." % (mod_path,cls_name,)if candidates:msg += " Choices are: %s." % ", ".join(candidates)raise ImportError(msg)else:# Re-trigger the module import exception.import_module(entry)# Check for obvious errors. (This check prevents duck typing, but# it could be removed if it became a problem in practice.)if not issubclass(app_config_class, AppConfig):raise ImproperlyConfigured("'%s' isn't a subclass of AppConfig." % entry)# Obtain app name here rather than in AppClass.__init__ to keep# all error checking for entries in INSTALLED_APPS in one place.if app_name is None:try:app_name = app_config_class.nameexcept AttributeError:raise ImproperlyConfigured("'%s' must supply a name attribute." % entry)# Ensure app_name points to a valid module.try:app_module = import_module(app_name)except ImportError:raise ImproperlyConfigured("Cannot import '%s'. Check that '%s.%s.name' is correct."% (app_name,app_config_class.__module__,app_config_class.__qualname__,))# Entry is a path to an app config class.return app_config_class(app_name, app_module)
  • ready(): 实例方法,在应用初始化完成后调用,一般用来注册信号和其他初始化操作。

Apps

属性

  • all_models: 存放app_label.model_nameModel的 mapping, 在 Model.new中调用apps.register_model完成注册。
  • app_configs: 存放AppConfig实例的 mapping。
  • stored_app_configs: 栈存放当前状态
  • apps_ready: 标志位,表示是否已经完成应用初始化。
  • models_ready: 标志位,表示是否已经完成模型初始化。
  • ready: 标志位,表示是否已经完成初始化。
  • _lock: 锁,用来控制并发访问。
  • loading: 标志位,表示是否正在加载。
  • _pending_operations: 存放延迟 Model 注册的操作。应对模型的关联问题。

重要函数

  • populate(): 实例方法,
  1. 根据传入的installed_apps遍历初始化应用,如果已经是 AppConfig,则直接使用;否则调用create方法创建.将初始化完成的 AppConfig 实例存入app_configs中。在此确保app 名字不允许重复
# Phase 1: initialize app configs and import app modules.
for entry in installed_apps:if isinstance(entry, AppConfig):app_config = entryelse:app_config = AppConfig.create(entry)# 不能重名if app_config.label in self.app_configs:raise ImproperlyConfigured("Application labels aren't unique, ""duplicates: %s" % app_config.label)self.app_configs[app_config.label] = app_configapp_config.apps = self# Check for duplicate app names.
# 可以用counter来统计重复
counts = Counter(app_config.name for app_config in self.app_configs.values()
)
duplicates = [name for name, count in counts.most_common() if count > 1]
if duplicates:raise ImproperlyConfigured("Application names aren't unique, ""duplicates: %s" % ", ".join(duplicates))
  1. 初始化各应用的模型
# Phase 2: import models modules.
for app_config in self.app_configs.values():app_config.import_models()self.clear_cache()self.models_ready = True
  1. 完成初始化
# Phase 3: run ready() methods of app configs.
for app_config in self.get_app_configs():# 调用每个appconfig的ready方法,完成自定义初始化步骤app_config.ready()self.ready = True
self.ready_event.set()
  • get_models(): 实例方法,返回所有注册的模型列表,带缓存。

# This method is performance-critical at least for Django's test suite.
@functools.cache
def get_models(self, include_auto_created=False, include_swapped=False):"""Return a list of all installed models.By default, the following models aren't included:- auto-created models for many-to-many relations withoutan explicit intermediate table,- models that have been swapped out.Set the corresponding keyword argument to True to include such models."""self.check_models_ready()result = []for app_config in self.app_configs.values():result.extend(app_config.get_models(include_auto_created, include_swapped))return result

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/745495.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Python | Bootstrap图介绍

在进入Bootstrap 图之前,让我们先了解一下Bootstrap(或Bootstrap 抽样)是什么。 Bootstrap 抽样(Bootstrap Sampling):这是一种方法,我们从一个数据集中重复地取一个样本数据来估计一个总体参数…

基于SpringBoot+Druid实现多数据源:原生注解式

前言 本博客姊妹篇 基于SpringBootDruid实现多数据源:原生注解式基于SpringBootDruid实现多数据源:注解编程式基于SpringBootDruid实现多数据源:baomidou多数据源 一、功能描述 配置方式:配置文件中实现多数据源,非…

Qt教程 — 3.1 深入了解Qt 控件:Buttons按钮

目录 1 Buttons按钮简介 1.1 Buttons按钮简介 1.2 Buttons按钮如何选择 2 如何使用Buttons按钮 2.1 QPushButton使用-如何自定义皮肤 2.2 QToolButton使用-如何设置帮助文档 2.3 QRadioButton使用-如何设置开关效果 2.4 QRadioButton使用-如何设置三态选择框 2.5 QCom…

学习使用postman软件上传文件发起api接口请求

学习使用postman软件上传文件发起api接口请求 设置headers头信息设置body 设置headers头信息 如图设置: KEY:Content-Type VALUE:multipart/form-data 设置body 设置需要上传的key对应的类型为File,上传类型 设置需要上传的文件…

留学生课设|R语言|研究方法课设

目录 INSTRUCTIONS Question 1. Understanding Quantitative Research Question 2. Inputting data into Jamovi and creating variables (using the dataset) Question 3. Outliers Question 4. Tests for mean difference Question 5. Correlation Analysis INSTRUCTIO…

如何安装ES

Elasticsearch入门安装 ES的官方地址:Elasticsearch 平台 — 大规模查找实时答案 | Elastic 我们进到网页可以看到platform(平台) 我们可以看到Elasticsearch logstash kibanba beats 这几个产品 Elasticsearch:分布式&…

某夕夕商品数据抓取逆向之webpack扣取

逆向网址 aHR0cHM6Ly93d3cucGluZHVvZHVvLmNvbQ 逆向链接 aHR0cHM6Ly93d3cucGluZHVvZHVvLmNvbS9ob21lL2JveXNoaXJ0 逆向接口 aHR0cHM6Ly9hcGl2Mi5waW5kdW9kdW8uY29tL2FwaS9naW5kZXgvdGYvcXVlcnlfdGZfZ29vZHNfaW5mbw 逆向过程 请求方式:GET 参数构成 【anti_content】…

基于Transformer的经典目标检测之DETR

背景 DETR,即DEtection TRansformer,是由尼古拉斯卡里翁及其团队于2020年在Facebook AI Research首次提出的,它在目标检测领域开创了一种新的波潮。 虽然目前并未保持最先进(State Of The Art)的地位,但DET…

vr虚拟现实游戏世界介绍|数字文化展览|VR元宇宙文旅

虚拟现实(VR)游戏世界是一种通过虚拟现实技术创建的沉浸式游戏体验,玩家可以穿上VR头显,仿佛置身于游戏中的虚拟世界中。这种技术让玩家能够全方位、身临其境地体验游戏,与游戏中的环境、角色和物体互动。 在虚拟现实游…

IP在网络通信中的重要作用

IP,全称Internet Protocol,即网际互连协议,是TCP/IP体系中的网络层协议。IP作为整个TCP/IP协议族的核心,是构成互联网的基础。它的作用重大且深远,下面将详细阐述IP的定义及其在网络通信中的重要作用。 首先&#xff0…

谈谈对chatgpt的看法

OpenAI数位Boss的长久坚持,始终以产品思维为导向,坚持专注,拿轮子造车子,终于发布了ChatGPT这款烧脑的经典款Chat Application,引领国内外一众fans跟风,有点摧枯拉朽的架势,关注了比较久&#x…

SpringBoot中的配置文件优先级、bootstrap和application的区别

SpringBoot中的配置文件优先级 SpringBoot项目当中支持的三类配置文件: application.properties application.yml application.yaml 在SpringBoot项目当中,我们要想配置一个属性,可以通过这三种方式当中的任意一种来配置都可以&#xff0…

Elastic Agent 的安装及使用

概述 Elastic Agent是Elastic Stack中的一个全新组件,旨在简化和统一监控和集成管理流程。它是一个轻量级的代理,可以部署到各种不同类型的主机和容器中,用于收集系统指标、日志和事件数据,并将其发送到Elasticsearch进行存储和分…

SpringBoot(自定义转换器+处理Json+内容协商)

文章目录 1.自定义转换器1.代码实例1.save.html2.编写两个bean1.Car.java2.Monster.java 3.WebConfig.java 配置类来自定义转换器4.测试 2.注意事项和细节1.debug查看转换器总数1.打断点2.执行到断点后,选左边的1923.可以看出,加上自定义的转换器一共125…

分类预测 | Matlab实现GSWOA-KELM混合策略改进的鲸鱼优化算法优化核极限学习机的数据分类预测

分类预测 | Matlab实现GSWOA-KELM混合策略改进的鲸鱼优化算法优化核极限学习机的数据分类预测 目录 分类预测 | Matlab实现GSWOA-KELM混合策略改进的鲸鱼优化算法优化核极限学习机的数据分类预测效果一览基本介绍程序设计参考资料 效果一览 基本介绍 GSWOA-KELM分类&#xff0…

react04- mvc 、 mvvm

MVC与MVVM stackoverflow论坛网站 react前端框架 使用框架前: 操作dom > js获取dom元素,事件侦听,修改数据,设置样式。。。 操作dom问题: 直接操作dom,会造成大量的回流、重绘,消耗大量性能操作起来也…

论文阅读——RingMo

RingMo: A Remote Sensing Foundation Model With Masked Image Modeling 与自然场景相比,RS图像存在以下困难。 1)分辨率和方位范围大:受遥感传感器的影响,图像具有多种空间分辨率。此外,与自然图像的实例通常由于重…

Microsoft VBA Excel 规律的Text文件转工作表Sheet

问题场景 简述: 在Excel的.xlsm文件中,有一个"RunControl"的sheet用来操控转换Text到指定的sheet中,需要在这个sheet上增加一个按钮,并在按钮上链接一个VBA程序,实现指定的功能。 以下是"RunControl&…

尚硅谷SpringBoot3笔记 (二) Web开发

Servlet,SpringMVC视频推荐:53_尚硅谷_servlet3.0-简介&测试_哔哩哔哩_bilibili HttpServlet 是Java Servlet API 的一个抽象类,用于处理来自客户端的HTTP请求并生成HTTP响应。开发人员可以通过继承HttpServlet类并重写其中的doGet()、do…

【图论】计算图的n-hop邻居个数,并绘制频率分布直方图

计算图的n-hop邻居个数,并绘制频率分布直方图 在图论中,n-hop邻居(或称为K-hop邻居)是指从某个顶点出发,通过最短路径(即最少的边数)可以到达的所有顶点的集合,其中n(或…