Opened 18 years ago

Closed 15 years ago

Last modified 11 years ago

#694 closed enhancement (wontfix)

[patch] TEMPLATE_DIRS should allow project root relative paths

Reported by: nirvdrum Owned by: Adrian Holovaty
Component: Template system Version: dev
Severity: normal Keywords:
Cc: sorin, moeffju Triage Stage: Unreviewed
Has patch: yes Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: no UI/UX: no

Description (last modified by Adrian Holovaty)

Many people develop their projects on one machine and deploy on another. The two (or more) different computers may not have the same filesystem layout and may not even be running the same OS. As such, it'd be nice if the requirement for absolute paths could be eliminated.

For my current django project, I have something like:

project/
   apps/
   templates/

It'd be nice if the templates directory could be specified relative to the project root.

Change History (12)

comment:1 by nirvdrum, 18 years ago

It appears that didn't format as well as I had planned. The idea is that project/ is the parent of apps/ and templates/.

comment:2 by Adrian Holovaty, 18 years ago

Description: modified (diff)
Resolution: invalid
Status: newclosed

(Fixed formatting in the description.)

TEMPLATE_DIRS is a setting, and each of your Django installations should have a separate settings file. This is how you designate different database passwords for different servers, for instance. The solution is to use separate settings files for your multiple environments.

Also, if that doesn't float your boat, you can use the "app_directories" template loader. See http://www.djangoproject.com/documentation/templates_python/#loader-types .

comment:3 by hugo, 18 years ago

And one should allways remember that settings files are just python: so you can just use "from basesettings import *" to pull in common settings that are the same accross different projects. Project settings really only need to set what is special for exactly this project.

Another idiom I find quite useful:

import os

TEMPLATE_DIRS = (
    os.path.expanduser('~/project/something/templates'),
)

works quite nice in projects that move to other servers and users when going production, but don't change in their structure itself.

comment:4 by Sune Kirkeby <sune.kirkeby@…>, 18 years ago

Resolution: invalid
Status: closedreopened
Summary: TEMPLATE_DIRS should allow project root relative paths[patch] TEMPLATE_DIRS should allow project root relative paths

Actually, adrian, that's a really poor excuse for not implementing this feature; if you specify a
relative path in your TEMPLATE_DIRS the only reasonable interpretation is that it's relative
to either your project-root or your settings-file. And, the different settings argument is hardly
relevant, relative TEMPLATE_DIRS are also broken for single-installation projects.

Besides, it's so simple to implement:

--- django/conf/settings.py     (/django/trunk) (revision 3075)
+++ django/conf/settings.py     (/django/patches/project-template_dirs) (revision 3075)
@@ -44,6 +44,21 @@
             setting_value = (setting_value,) # In case the user forgot the comma.
         setattr(me, setting, setting_value)
 
+# TEMPLATE_DIRS are relative to the directory containing the top-level
+# module of DJANGO_SETTINGS_MODULE.
+if '.' in me.SETTINGS_MODULE:
+    name, _ = me.SETTINGS_MODULE.split('.', 1)
+    project_mod = __import__(name, '', '', [''])
+else:
+    project_mod = mod
+project_root = os.path.dirname(project_mod.__file__)
+
+if os.path.isdir(project_root):
+    me.TEMPLATE_DIRS = [
+        os.path.abspath(os.path.join(project_root, os.path.expanduser(path)))
+        for path in me.TEMPLATE_DIRS
+    ]
+
 # save DJANGO_SETTINGS_MODULE in case anyone in the future cares
 me.SETTINGS_MODULE = os.environ.get(ENVIRONMENT_VARIABLE, '')

comment:5 by Adrian Holovaty, 18 years ago

Resolution: wontfix
Status: reopenedclosed

Because the settings files are pure Python, you can calculate the relative paths directly in the settings files. I'm marking this (again) as a wontfix.

comment:6 by aljungberg, 15 years ago

The posted solution, to have a settings file for every installation location, is insufficient for our needs. That solution creates two distinct problems:

  1. Every developer on the project is forced to have one or more settings files as they check out the project source code into different folders. Or each developer hacks their settings.py file to match their own situation which leads to merge conflicts.
  2. Requiring manual changes between production and test environments increases the risk of problems that only occur during production deployment.

We implemented the alternative solution from adrian's last comment and I will share it here for quick reference for other users who run into this particular limitation.

In settings.py,

import os
PROJECT_PATH = os.path.abspath(os.path.split(__file__)[0])

TEMPLATE_DIRS = (
    os.path.join(PROJECT_PATH, "templates"),
)

If this ticket is revisited in the future it is my opinion that it should be implemented as suggested to promote 'batteries included' and 'keep it simple' philosophies in Django.

comment:7 by sio4, 15 years ago

Resolution: wontfix
Status: closedreopened

I'm newbie to django, and this page is the result of one of my few searches about django. It means, IMHO, maybe many newbies can confuse on this issue like me.

my question is: "why we should use relative path for templates directory setting? It is always same in relative(for many cases) but it is different in absolute.(and how many times is it placed on outside of project?) then why we all do add three same lines into settings.py everytime? (import os, project_path=..., os.path.join...)" can I get some reasonable reason?

"app_directories template loader" is not a good solution because the look&feel is site specific rather than application specific. (app_directories template loader is usefull for drop-in applications instead.)

please excuse my poor English. thank you for your consideration.

comment:8 by James Bennett, 15 years ago

Resolution: wontfix
Status: reopenedclosed

This was marked "wontfix" by a core developer. If you disagree, start a thread on the django-developers list.

comment:9 by sorin, 14 years ago

Cc: sorin added
Version: SVN

Please reconsider this issue, it is #1 having more than 100 votes on http://stackoverflow.com/questions/550632/favorite-django-tips-features

Implementing this will improve user experience and simplify deployment.

The fact that people can change the code is not an excuse not to do the right thing.

in reply to:  8 comment:10 by James Bennett, 14 years ago

Quoting myself: If you disagree, start a thread on the django-developers list.

So if you feel strongly about this, you know what to do.

comment:11 by moeffju, 11 years ago

Cc: moeffju added
Easy pickings: unset
UI/UX: unset

comment:12 by anonymous, 11 years ago

Has this been fixed?

Note: See TracTickets for help on using tickets.
Back to Top