Skip to content

Commit 08ca7b9

Browse files
committed
Fixed #35485 Added how to guide for project and app templates.
1 parent b9aa323 commit 08ca7b9

File tree

1 file changed

+248
-0
lines changed

1 file changed

+248
-0
lines changed
Lines changed: 248 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,248 @@
1+
==============================================================
2+
How to override project and app file structure using templates
3+
==============================================================
4+
5+
6+
Introduction
7+
============
8+
9+
The first command you will run when setting up a django project is
10+
:djadmin:`startproject`. Having set up your project, you will then start
11+
creating your apps with :djadmin:`startapp`. Each of these commands will create
12+
a file structure that is based on default templates within the Django
13+
repository.
14+
15+
However, you can create your own templates so that when you run
16+
:djadmin:`startproject` or :djadmin:`startapp` it creates the app and project
17+
structure that is best for you.
18+
19+
What the defaults look like
20+
===========================
21+
22+
The command :djadmin:`startproject` will create the ``manage.py`` file, along
23+
with a folder named after the ``project_name`` parameter passed in the initial
24+
command. Here the command is run with the project name as ``myproject``:
25+
26+
.. console::
27+
28+
$ django-admin startproject myproject .
29+
30+
The resulting file structure is based on the default template-file structure in
31+
(:source:`django/conf/project_templates`). There, each file has the extension
32+
``.py-tpl`` to denote the file as a template. Each template contains template
33+
tags that end up being filled from the command and django version context. The
34+
template context is detailed at the end of the documentation for
35+
:djadmin:`startproject`.
36+
37+
The resulting files all have the ``.py`` file extension and are ready to be
38+
used:
39+
40+
.. code-block:: none
41+
42+
myproject/
43+
manage.py
44+
myproject/
45+
__init__.py
46+
asgi.py
47+
settings.py
48+
urls.py
49+
wsgi.py
50+
51+
A similar thing happens when you run :djadmin:`startapp`. Both commands inherit
52+
from the same ``TemplateCommand`` class (in
53+
:source:`django/core/management/templates.py`), but they discern between app
54+
and project.
55+
56+
A typical command to initialize an app with the name ``myapp``:
57+
58+
.. console::
59+
60+
$ python manage.py startapp myapp .
61+
62+
This creates an app in the current directory with the default file structure
63+
found in (:source:`django/conf/app_templates`). As above, each template has
64+
the extension ``.py-tpl`` to denote the file as a template, but is copied over
65+
as a python file. Each template contains template tags for the variables that
66+
will be passed.
67+
68+
.. code-block:: none
69+
70+
myapp/
71+
__init__.py
72+
admin.py
73+
apps.py
74+
migrations/
75+
__init__.py
76+
models.py
77+
tests.py
78+
views.py
79+
80+
81+
Creating your own Project and App Templates
82+
===========================================
83+
84+
The default project and app file structures are the ones suggested by django,
85+
but not the only ones that can be used. Because django does not require a
86+
specific file structure for the ``settings`` or ``urls`` files, you can create
87+
your own structure. The only thing to watch out for is that the imports and
88+
references to other modules is correct. As long as the files find each other,
89+
it doesn't matter where they are placed.
90+
91+
The folders that contain your templates can have any naming convention.
92+
``new_django_template`` is as valid as ``files_structure``. You can even have
93+
them as a directory, as a zip file or a compressed or uncompressed archive. In
94+
addition, you can pull them from the web as long as they are in a valid format.
95+
96+
File and folder naming conventions
97+
----------------------------------
98+
99+
There is, however, a specific naming convention that needs to be followed in
100+
order to have your project name as the folder name enclosing the settings
101+
files. In the project template, the folder that uses the name you pass in the
102+
:djadmin:`startproject` command must be named ``project_name``. This name is
103+
then replaced by the name you enter when you run the command. In the example at
104+
the top of the page the template folder ``project_name`` would be replaced
105+
with ``myapp``.
106+
107+
For the :djadmin:`startapp` command, this is not necessary, as the folder
108+
enclosing the files ``admin.py`` and ``urls.py`` is the folder of the app
109+
template, and the command will take the contents of this folder, and move them
110+
to a folder with the name passed in the command.
111+
112+
However, you can leverage the app name or project name if you have a file or
113+
folder that needs to use the name. Because this substitution happens using
114+
Python's string ``replace`` function, you can have something like a separate
115+
settings folder in your template with the name ``project_name_settings`` and
116+
the folder name will be changed, as in the above example to
117+
``myproject_settings``. The same is true for files with ``project_name`` as
118+
part of their name. For apps, you should have folders or files with
119+
``app_name`` within their name. In our example, ``app_name`` would be replaced
120+
by ``myapp`` and ``app_name_utilities`` would be replaced by
121+
``myapp_utilities``.
122+
123+
File structure of the templates
124+
-------------------------------
125+
126+
Neither the :djadmin:`startproject` nor the :djadmin:`startapp` commands
127+
generate the code in the files. They only copy existing files and (when
128+
applicable) insert the context. When the files are copied from a custom project
129+
template, they are copied directly without any code modifications from the
130+
default templates. It is up to the developer to make sure that the template
131+
file structure and code actually works, and that they contain up-to-date code,
132+
settings, and variables for the version of django being used. When updating the
133+
Django version, it is recommended to double-check against the default project
134+
or app template files to see what has been added or changed. It is highly
135+
recommended to start a django project first, make sure that the files work
136+
together, and then create a template based on that file structure and content.
137+
138+
As a example, a flat Django project can look like this, with all of the files
139+
normally found in the project folder outside that folder, and at the same level
140+
as ``manage.py``:
141+
142+
.. code-block:: none
143+
144+
myproject/
145+
asgi.py
146+
manage.py
147+
settings.py
148+
urls.py
149+
wsgi.py
150+
151+
152+
In this particular instance, to make the files work with each other, you'd have
153+
to adapt the settings reference in ``manage.py`` to refer to ``"settings"``
154+
instead of ``"myproject.settings"`` since your ``settings.py`` file is no
155+
longer in the created ``myproject`` folder, but at the same level as
156+
``manage.py``. Likewise in ``settings.py``, you'd have to change the value of
157+
:settings:`ROOT_URLCONF` from ``"myproject.urls"`` to simply ``"urls"`` and
158+
:settings:`WSGI_APPLICATION` from ``"myproject.wsgi.application"`` to
159+
``"wsgi.application"``.
160+
161+
For the :djadmin:`startapp` command, there is less that can be customized since
162+
it is a single folder with files and a migrations folder within. If certain
163+
files are not needed they can be left out. For example, if no models will be
164+
used, the ``models.py`` file and the ``migrations`` folder can be left out. In
165+
this case the ``admin.py`` file could also be left off. Conversely, if you
166+
always use custom managers, you could add a ``managers.py`` file to your custom
167+
structure to make sure the file is always there.
168+
169+
Template suffixes
170+
-----------------
171+
172+
For convenience, python files used in the templates use the suffix ``.py-tpl``.
173+
During the process of creating the project or app files, the suffix is changed
174+
to ``.py``. However, this is not absolutely necessary, since any files with the
175+
``.py`` suffix can have the context changed by the templating engine if they
176+
contain template tags that are variables.
177+
178+
179+
Templating non-Python files
180+
---------------------------
181+
182+
Since the commands that use the templates just copy files, you can have any
183+
type of file in the project or app template. This is especially useful if you
184+
want to set up frontend or infrastructure files within the project template.
185+
186+
Any type of file is supported as long as it doesn't end with ``.pyo``,
187+
``.pyc``, or ``.py.class``. Any type of directory is supported as long as it
188+
doesn't begin with a period ``.`` (hidden directory) or is a ``__pycache__``
189+
file.
190+
191+
You can even use the template engine to fill in ``{{ project_name }}`` in
192+
places where the project name would be commonly used by other apps, such as in
193+
Kubernetes or Docker files.
194+
195+
196+
Excluding parts of files from templating
197+
----------------------------------------
198+
199+
The templating engine will overwrite any context variables found in the project
200+
or app template. Sometimes, for the purposes of documentation, you want to
201+
leave the variables visible in the produced app or project structure. To have
202+
``{{ django_version }}`` or ``{{ project_name }}`` still visible in the
203+
resulting file, you can wrap that part of the file, or even the whole file with
204+
the template tags ``{% verbatim %}`` and ``{% endverbatim %}``. The templating
205+
engine will end up removing them from the finished file.
206+
207+
208+
Using your templates
209+
====================
210+
211+
The basic command to start your project using your new template is:
212+
213+
.. console::
214+
215+
$ django-admin startproject myproject .
216+
217+
To add non-python files to the templating engine, add the names to the
218+
``extension`` flag like so:
219+
220+
.. console::
221+
222+
$ django-admin startproject myproject . --extension js,toml
223+
224+
So now all Javascript and toml files will be run through the templating engine
225+
to replace any variables.
226+
227+
If you are using any non-python files that you need run through the templating
228+
engine that do not have extensions, such as ``Dockerfile`` or ``.gitignore``,
229+
or for files with extensions in which only some files should go through the
230+
template engine, you can add them individually after the ``name`` flag:
231+
232+
.. console::
233+
234+
$ django-admin startproject myproject . --name Dockerfile,.gitignore
235+
236+
To exclude any directories from being affected by the template engine, you can
237+
use the ``exclude`` flag and they will be removed from the folders to go
238+
through templating:
239+
240+
.. console::
241+
242+
$ django-admin startproject myproject . --exclude frontend,reference
243+
244+
The flag usage above holds true for ``python manage.py startapp .``, but,
245+
instead, you would be working on the app level instead of the project level.
246+
247+
For more information, you can visit the documentation for
248+
:djadmin:`startproject` and :djadmin:`startapp`.

0 commit comments

Comments
 (0)