Django如何查找和加载模板的路径是什么?

104 投票
15 回答
212838 浏览
提问于 2025-04-15 23:57

我正在Windows 7环境下跟着这个教程学习。

我的设置文件里有这样的定义:

TEMPLATE_DIRS = (
    'C:/django-project/myapp/mytemplates/admin'
)

我从Django自带的管理模板目录(django/contrib/admin/templates)中找到了base_template,这个模板的文件名是admin/base_site.html。按照教程的指示,我把它放到了myapp目录下的一个admin子目录里,但不知道为什么它似乎没有生效。

有没有人知道可能是什么问题呢?

15 个回答

15

在Django 2.0.3中,有一个聪明的方法可以把模板文件放在项目目录里,路径是 (/root/templates/app_name):

首先,你需要在 settings.py 文件中进行一些设置:

BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
TEMP_DIR = os.path.join(BASE_DIR, 'templates')
...
TEMPLATES = [
{
    'BACKEND': 'django.template.backends.django.DjangoTemplates',
    'DIRS': [TEMP_DIR],
...

然后,在 views.py 文件中,只需添加这样的模板路径:

app_name/html_name
43

如果使用的是Django的默认设置,那为什么不直接用它自带的、预定义的BASE_DIR和TEMPLATES呢?在通过pip安装的Django(版本1.8)中,我得到了:

BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) 


TEMPLATES = [
    {
        'BACKEND': 'django.template.backends.django.DjangoTemplates',
        'DIRS': [
            ### ADD YOUR DIRECTORY HERE LIKE SO:
            BASE_DIR + '/templates/',
        ],
        'APP_DIRS': True,
        'OPTIONS': {
            'context_processors': [
                'django.template.context_processors.debug',
                'django.template.context_processors.request',
                'django.contrib.auth.context_processors.auth',
                'django.contrib.messages.context_processors.messages',
            ],
        },
    },
]
208

我知道这不是Django教程里的内容,真是让人失望,不过为了你的路径变量,最好设置相对路径。你可以这样设置:

import os.path

PROJECT_PATH = os.path.realpath(os.path.dirname(__file__))

...

MEDIA_ROOT = os.path.join(PROJECT_PATH, 'media/')

TEMPLATE_DIRS = [
    os.path.join(PROJECT_PATH, 'templates/'),
]

这样的话,你可以随意移动你的Django项目,路径根就会自动更新。这在你设置生产服务器的时候特别有用。

其次,你的TEMPLATE_DIRS路径看起来有点问题。它应该指向你模板目录的根目录。而且,路径的最后应该有一个斜杠/

我猜测.../admin/这个目录并不是你的模板根目录。如果你还是想写绝对路径,就应该去掉对admin模板目录的引用。

TEMPLATE_DIRS = [
    'C:/django-project/myapp/mytemplates/',
]

说到这里,模板加载器默认应该设置为递归地进入你的应用目录,去寻找模板文件。

TEMPLATE_LOADERS = [
    'django.template.loaders.filesystem.load_template_source',
    'django.template.loaders.app_directories.load_template_source',
    # 'django.template.loaders.eggs.load_template_source',
]

除非你特别想覆盖某些东西,否则你不需要复制admin模板。

如果你还没有运行过syncdb,你需要先运行一次。如果你是通过runserver来托管Django,还需要静态服务你的媒体文件。

撰写回答