[Django 0-1] Core.Checks 模块

Checks 源码分析

Django 的 checks 模块提供了一系列的检查函数,用于检查 Django 项目的配置是否正确。

文件结构

shell 复制代码
.
├── __init__.py
├── async_checks.py
├── caches.py
├── compatibility
│   ├── __init__.py
│   └── django_4_0.py
├── database.py
├── files.py
├── messages.py
├── model_checks.py
├── registry.py
├── security
│   ├── __init__.py
│   ├── base.py
│   ├── csrf.py
│   └── sessions.py
├── templates.py
├── translation.py
└── urls.py

3 directories, 17 files

可以学习的地方

  • 对项目的可靠性检查方面可以借鉴 Django 的设计,可以包括

    • 内置的 contrib 如 admin
    • async_support 特性检查,如是否在不支持的环境下开启了异步支持
    • 缓存配置检查,如是否使用了过期时间短的缓存
    • 数据库配置检查,如是否使用了过期时间短的数据库连接
    • 模型检查,如是否有重复的模型名称
    • 安全检查,如是否开启了 CSRF 保护,是否使用了过期时间短的 session
    • 模板检查
    • 翻译检查
    • URL 检查
    • siangls 检查
    • files 文件系统检查
  • 使用inspect.func_accepts_kwargs函数,强制让函数参数中包含**kwargs

    同样的函数还有func_accepts_var_args,强制让函数参数中包含*args
    func_supports_parameter置顶

  • core/checks/registry.py CheckRegistry 类方法提供了利用装饰器机制封装了函数register用于注册检查。

python 复制代码
class CheckRegistry:

    def __init__(self):
        self.registered_checks = set()
        self.deployment_checks = set()

    def register(self, check=None, *tags, **kwargs):
        """
        Can be used as a function or a decorator. Register given function
        `f` labeled with given `tags`. The function should receive **kwargs
        and return list of Errors and Warnings.

        Example::

            registry = CheckRegistry()
            @registry.register('mytag', 'anothertag')
            def my_check(app_configs, **kwargs):
                # ... perform checks and collect `errors` ...
                return errors
            # or
            registry.register(my_check, 'mytag', 'anothertag')
        """

        def inner(check):
            if not func_accepts_kwargs(check):
                raise TypeError(
                    "Check functions must accept keyword arguments (**kwargs)."
                )
            check.tags = tags
            checks = (
                self.deployment_checks
                if kwargs.get("deploy")
                else self.registered_checks
            )
            checks.add(check)
            return check

        # 如果你的check函数是一个callable对象,那么直接返回inner(check)
        if callable(check):
            return inner(check)
        else:
            if check:
                tags += (check,)
            return inner
  • 为项目建立一个 runtime 检查机制,通过这些 checks 来确保项目的运行正确。

id 可以确保所有 errors 和 warnings 的唯一性,并提供一种过滤 id 和 level 机制来忽略特定的错误。

python 复制代码
class CheckMessage:
    def __init__(self, level, msg, hint=None, obj=None, id=None):
        if not isinstance(level, int):
            raise TypeError("The first argument should be level.")
        self.level = level
        self.msg = msg
        self.hint = hint
        self.obj = obj
        self.id = id

    def __eq__(self, other):
        return isinstance(other, self.__class__) and all(
            getattr(self, attr) == getattr(other, attr)
            for attr in ["level", "msg", "hint", "obj", "id"]
        )

    def __str__(self):
        from django.db import models

        if self.obj is None:
            obj = "?"
        elif isinstance(self.obj, models.base.ModelBase):
            # We need to hardcode ModelBase and Field cases because its __str__
            # method doesn't return "applabel.modellabel" and cannot be changed.
            obj = self.obj._meta.label
        else:
            obj = str(self.obj)
        id = "(%s) " % self.id if self.id else ""
        hint = "\n\tHINT: %s" % self.hint if self.hint else ""
        return "%s: %s%s%s" % (obj, id, self.msg, hint)

    def __repr__(self):
        return "<%s: level=%r, msg=%r, hint=%r, obj=%r, id=%r>" % (
            self.__class__.__name__,
            self.level,
            self.msg,
            self.hint,
            self.obj,
            self.id,
        )

    def is_serious(self, level=ERROR):
        return self.level >= level

    def is_silenced(self):
        from django.conf import settings

        return self.id in settings.SILENCED_SYSTEM_CHECKS


class Debug(CheckMessage):
    def __init__(self, *args, **kwargs):
        super().__init__(DEBUG, *args, **kwargs)


class Info(CheckMessage):
    def __init__(self, *args, **kwargs):
        super().__init__(INFO, *args, **kwargs)


class Warning(CheckMessage):
    def __init__(self, *args, **kwargs):
        super().__init__(WARNING, *args, **kwargs)


class Error(CheckMessage):
    def __init__(self, *args, **kwargs):
        super().__init__(ERROR, *args, **kwargs)


class Critical(CheckMessage):
    def __init__(self, *args, **kwargs):
        super().__init__(CRITICAL, *args, **kwargs)
相关推荐
湫ccc5 小时前
《Python基础》之字符串格式化输出
开发语言·python
mqiqe6 小时前
Python MySQL通过Binlog 获取变更记录 恢复数据
开发语言·python·mysql
AttackingLin6 小时前
2024强网杯--babyheap house of apple2解法
linux·开发语言·python
哭泣的眼泪4086 小时前
解析粗糙度仪在工业制造及材料科学和建筑工程领域的重要性
python·算法·django·virtualenv·pygame
湫ccc7 小时前
《Python基础》之基本数据类型
开发语言·python
drebander8 小时前
使用 Java Stream 优雅实现List 转化为Map<key,Map<key,value>>
java·python·list
威威猫的栗子8 小时前
Python Turtle召唤童年:喜羊羊与灰太狼之懒羊羊绘画
开发语言·python
墨染风华不染尘8 小时前
python之开发笔记
开发语言·笔记·python
Dxy12393102169 小时前
python bmp图片转jpg
python
麦麦大数据9 小时前
Python棉花病虫害图谱系统CNN识别+AI问答知识neo4j vue+flask深度学习神经网络可视化
人工智能·python·深度学习