Django app應用的配置載入過程
阿新 • • 發佈:2021-06-12
wsgi.py
import os
from django.core.wsgi import get_wsgi_application
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "apc.settings")
application = get_wsgi_application() #獲取application
django.core.wsgi.py
import django from django.core.handlers.wsgi import WSGIHandler def get_wsgi_application(): """ The public interface to Django's WSGI support. Return a WSGI callable. Avoids making django.core.handlers.WSGIHandler a public API, in case the internal WSGI implementation changes or moves in the future. """ django.setup(set_prefix=False) # Django 初始化,點進去檢視 return WSGIHandler()
django.init.py
def setup(set_prefix=True): """ Configure the settings (this happens as a side effect of accessing the first setting), configure logging and populate the app registry. Set the thread-local urlresolvers script prefix if `set_prefix` is True. """ from django.apps import apps from django.conf import settings from django.urls import set_script_prefix from django.utils.log import configure_logging configure_logging(settings.LOGGING_CONFIG, settings.LOGGING) if set_prefix: set_script_prefix( '/' if settings.FORCE_SCRIPT_NAME is None else settings.FORCE_SCRIPT_NAME ) apps.populate(settings.INSTALLED_APPS) # 從配置中讀取註冊的app,然後填充每個app對應的配置
django.app.registry.Apps
def populate(self, installed_apps=None): if self.ready: # 保證應用配置只填充一次 return with self._lock: if self.ready: return if self.loading: # Prevent reentrant calls to avoid running AppConfig.ready() # methods twice. raise RuntimeError("populate() isn't reentrant") self.loading = True # Phase 1: initialize app configs and import app modules. for entry in installed_apps: if isinstance(entry, AppConfig): # 註冊的時候指定的是AppConfig app_config = entry else: app_config = AppConfig.create(entry) # 如果註冊app時指定的是app的名稱,則會根據app的default_app_config屬性查詢對應的配置 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_config app_config.apps = self # Check for duplicate app names. 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)) self.apps_ready = True # Phase 2: import models modules. for app_config in self.app_configs.values(): app_config.import_models() # 根據label 確認models self.clear_cache() self.models_ready = True # Phase 3: run ready() methods of app configs. for app_config in self.get_app_configs(): app_config.ready() # 執行配置中定義的ready 方法 self.ready = True
因此,配置app 有兩種方式。
一種是直接定義繼承AppConfig 的配置類,將該類註冊在settings中;
一種是在app的settings中註冊最外層的應用名稱,然後給app賦值default_app_config屬性,使用該屬性指向定義的AppConfig 類,這種方式可以多個app共用同一個配置