Django's Double Folder Structure
In the previous lesson, you created a template, and now you’re going to see how to set it up. In production, Django eventually collects all of the templates in various folders and puts them all together in one folder for all the templates.
That can work fine, but there can be some problems with a flat folder structure, so it can be best to use a double folder structure instead.
00:00
In the previous video, we created a template and linked it correctly, so now you might be wondering, “Why do you not just drop this index.html
right into the templates/
folder? Why is there this extra folder in there?”
00:13 I want to show you why that’s the case. So, remember that this is the better way to set it up: with this nested folder structure. Let’s take a look at why that’s the case. So, we were thinking about maybe we just do a flat folder structure. How would that look like, and is there a problem with it?
00:34
Assume that in our example Django project, we have three apps. We have the projects
app, the one we just created, and the templates/
folder, inside of there. We have another app with a templates/
folder and yet another app with a templates/
folder.
00:48
What Django does is that in production, eventually, it collects all of those templates, everything that sits inside of a folder called templates
, something that you define inside of these template directories, and puts it all together into one folder for all the templates.
01:04 So, this is not necessarily a problem yet,
01:08
and this can work fine. I have, like, index.html
here, I have site.html
there, and I have project_list.html
here.
01:17
They all come together. Django is going to know which one to find and which one to render. However, there’s some possible troubles with this flat folder structure, and that’s why we want to avoid it. So, we’ve created this index.html
file, which is a very common name for an HTML file.
01:34
Let’s assume that all of our apps might have an index.html
file. What happens in production? All of those files get pulled together into the big templates/
folder, and Django doesn’t know which index.html
files to render, so there is a problem here. Now, this double folder structure that we created before, is the solution to this issue. If, inside of each of those folders, we create another one that just has the same name as our app—so, projects/templates/
and inside, other projects/
folder. app2/templates
, another folder called app2
, et cetera—and then inside of there, we can have index.html
files in each of them. It doesn’t matter.
02:18 We don’t have to worry about double naming, which—as long as your app is really small—might not be a problem, but if the project grows and you have multiple apps in there, this could become a problem.
02:29
You might accidentally have the same named templates and then run into unexpected problems. If you have it set up like this, with a double folder structure, then what Django does is it collects everything, it collects the folder as well as the files, and puts them all together into this big templates/
folder.
02:48
That’s great because then, this makes the paths unambiguous, and it’s always clear and obvious for Django what is the right template to render. So eventually, you’re going to end up with a folder structure like this: the big templates/
folder containing everything, containing a folder that’s named after your app, and inside of there, the app-specific templates.
03:09
That gets a big green checkmark because we’re avoiding some problems. All right. So, I hope this explains to you why we want to do this double folder structure like this projects/templates/projects/
.
03:23 It’s essentially just to avoid some troubles that you could run into in the future. Let’s start with good habits right from the beginning. Okay, that’s it for this video. Next, we’re going to change our HTML template a little bit and add Bootstrap styling to it. See you in the next video!
reblark on Oct. 31, 2019
So that I understand the file structure more clearly, the first thing I do is create a folder to put all my work for django in, for instance django-portfolio. But then I create a sub-folder, for instance projects, which becomes my apps central folder(it could be “portolio”. In that folder, I put whatever apps I want to build in this structure. So, I might build an app called “projects” and an app called “monies” and an app called “travels.” Inside each of these apps will be the files from init.py to views.py and inside the views.py app will be the templates that will be used by each of the apps above and contained in that app structure. So, all the files in views.py in each app will have the app name in its path and live in the templates folder as app/commonname. The point being that in the total structure, templates lives above all the app structures and collects all the templates from all the apps into its one folder. (Not sure about how well I wrote this but I think I have the point.)
deodesumitsingh on Dec. 28, 2019
I learned alot with this single video. Thank you alot for sharing Django project structure in simple terms.
Martin Breuss RP Team on Jan. 23, 2020
Glad it was useful @deodesumitsingh! :)
Samuel Barbosa on Jan. 28, 2020
I had never paid attention to that detail. Thanks @mbreuss
Ken on May 15, 2020
Really liking this tutorial so far. Most clear and understandable one I have run into so far. Haven’t had any questions pop up that weren’t answered. Other tutorials just were confusing.
Hector Perea Mosquera on July 13, 2020
So far, the best Django tutorial that I’ve seen so far. Very useful, and the folder structure explanation was very clear. Thanks a lot for this.
CCC on Oct. 9, 2020
Thank you for visualizing the problem, this explained the problem and the solution in very clear terms!
Lots of tutorial online would gloss over this or not even mention it until it’s a problem, but you show us best practices from the beginning even if it may confuse some.
Many thanks Martin, you’re a great teacher, mate.
Martin Breuss RP Team on Oct. 9, 2020
Thanks for all the nice comments @Samuel Barbosa, @ken4, @Hector Perea Mosquera and @CCC! 😀 Glad you’re finding the explanations helpful.
I remember being pretty confused about errors coming from an incorrectly set up folder structure myself and how a big lightbulb turned on when I finally got it 💡 !
abykal on April 3, 2021
Hi, I have a question. Instead of making templates folder in each app, why can’t me make a single template folder in main project directory, with separate directories for each app? This way, we can even have common templates under main directory.
Any comments?
abykal on April 3, 2021
Also, it was mentioned in slide that structure of ‘templates’ was within main project. But, PyCharm has ‘templates’ created under projects app. PyCharm - screenshot
Bartosz Zaczyński RP Team on April 6, 2021
@abykal It’s a matter of preference. However, one advantage to keeping the templates in the app subfolder is portability. That way, you can reuse the same app, including its templates, in a different Django project.
sndselecta on May 31, 2021
Still a bit confused about directory structure (similar question to reblark). The portfolio directory in the main directory for djangos functionality, all config files are contained there. The projects (app # 1) folder is a specific web application with its unique, models, url routes, views, templates (html files to be rendered). Every other web application (app #2, app #3, app #4 etc....) will sit at the same level as the projects and portfolio, with their own unique models, url routes, views, templates (html files to be rendered). Why would we include multiple apps in the same overall folder (parent folder to portfolios, projects (app#1), app #2, app #3, app #4 etc.... Im assuming this has something to do with reusability, but from a security and deployment perspective wouldn’t this be counter productive when scaled?
sndselecta on May 31, 2021
Why would the templates folder of many apps be merged? Why would we merge multiple apps?
Martin Breuss RP Team on May 31, 2021
Hi @sndselecta! I think you understood the folder structure correctly:
portfolio/ # the django project folder
│
├── portfolio/ # the management app
│ # --snip--
│ └── settings.py
│
├── projects/ # a "normal" Django app
│ ├── __init__.py
│ # --snip--
│ └── templates/
│ └── projects/
│ └── # this app's .html files
│
├── another_app/ # another "normal" Django app
│ ├── __init__.py
│ # --snip--
│ └── templates/
│ └── another_app/
│ └── # this app's .html files
│
└── manage.py
About your other questions, let’s see:
Why would the templates folder of many apps be merged?
Because it allows Django to serve all the template content from a single source folder. This makes it easier to handle when it’s running.
In the end you’re serving one Django project - the project is your web app. I know it gets confusing with so many things being called an “app”!
You’re collecting all the templates from all your Django apps in order to serve them from one place for your whole Django project, which is the web app that you’re building and deploying.
Why would we merge multiple apps?
You’re never merging the Django apps. You keep the code for each of them separate because they represent different functional parts of your web application. And because it makes that functionality portable to other web applications.
What Django does, as mentioned above, is that it collects some of the content of each of your Django apps and serves them from a single location in your Django project.
This happens automatically when you use the built-in development server runserver
.
Hope that helps to clarify things!
sndselecta on May 31, 2021
So ‘another_app’ is the same web application but another feature or just another view? If another feature can you give an example of what it could be? Also you are saying that everything in the parent portfolio folder is one web application. I think a better way to explain this would be to use more meaningful folder names, like:
parent --> portfolio/ (instead use) Web_application_1
parent.child --> portfolio/ (instead use) Web_application_1_management
parent.child--> projects/ (instead use) Web_application_1_func_main
parent.child --> another_app/ (instead use) Web_application_1_func_feature_1
The long names can be refactored to smaller, once the user has grasped the fundamentals of the folder hierarchy. Can u give an example of what you mean by “because it makes that functionality portable to other web applications”, i think in video it was referred to as pluggable. I understand why the templates being refactored into one main file as Ive done ruby on rails, which does the same for all html, css and js, so I understand that part. Thank you for the explanation so far.
Martin Breuss RP Team on June 1, 2021
Hi again @sndselecta.
Great, glad you found a way to reframe it so it makes sense to you 👍 I personally don’t find the long names easier to grasp, but learning and understanding is a personal process and different for different people. Thanks for posting your thoughts here, it’ll probably help some other learners as well!
As for what is a feature that deserves its own Django app, that’s a point of discussion and there’s no hard rule to it. You can find some good suggestions when you google for it, but as a rule-of-thumb you can create a new app when it’s a relatively separate topic from the rest of the Django project, e.g.:
- projects
- blog
- conferences
- etc.
These are all different aspects of a web application that would each benefit if you built their code in their own separate Django apps.
Pluggable Apps
Inside of each Django app, you define the models, views, routing, and templates. If you set it up in the way as discussed in this course, then you can literally copy one of your app folders (e.g. projects
in my example), and paste it into another Django project (= another web application) that you built.
As a specific example: Let’s say you create WordPress themes for a living. You might want to display your projects not only in a portfolio web application, but also in an online store where you sell your themes.
You could create a new Django project that will be your e-commerce store and live on a different server and a different URL. It’ll be a completely separate web application than your portfolio site. However, because you built your projects
Django app in a pluggable manner, you can copy-paste the app folder into your new Django project. Then you only need to:
- add the app’s name in
settings.py
- route to your app’s
urls.py
file from the management app’surls.py
file - make and apply the migrations
After that you’re good to go and you have all the functionality to display your projects in your new store web application, too.
Singular Template Folder
Just to clarify this, the templates don’t get refactored into a one main file, that might be a misunderstanding.
Django collects all the template files from all your Django apps and puts them into one shared templates folder. The files still remain individual files.
sndselecta on June 1, 2021
I see about the templates refactored into one file vs refactored into one folder. And just to confuse everyone further when you say pluggable you mean you essentially create an interchangeable web application which we can be used as an interchangeable template between different web applications so that you don’t have to rebuild that specific web application from scratch just modify a few settings and its good to go fully functionally into a completely separate web application. So each app folder (portfolio and projects) listed below is a completely different web application but the management app, is the settings for all the apps? If I copy projects to another web application folder then i would have to do the following for corresponding management folder (equivalent of portfolio/portfolio`
- add the app’s name in settings.py
- route to your app’s urls.py file from the management app’s urls.py file
- make and apply the migrations
portfolio/ # the django project folder
│
├── portfolio/ # the management app
│ # --snip--
│ └── settings.py
│
├── projects/ # a "normal" Django app
│ ├── __init__.py
│ # --snip--
│ └── templates/
│ └── projects/
│ └── # this app's .html files
│
├── another_app/ # another "normal" Django app
│ ├── __init__.py
│ # --snip--
│ └── templates/
│ └── another_app/
│ └── # this app's .html files
│
└── manage.py
Martin Breuss RP Team on June 2, 2021
Hm, I’m not sure, we might be talking past each other here? But it might just be a question of using the right terms, so let me try to clarify them here:
- Django project: This is a web application (= a website that has a dynamic component to it, meaning that content gets created at the request of the user). It contains one or more functional parts that are called Django apps.
- Django app: A distinct functional part of a Django project. There can be one or more of them for each project.
- Management app: The first Django app that gets created when you set up the project is a bit different than subsequent apps. I call this one the “management app” because it contains e.g. the
settings.py
file that keeps the settings for your whole Django project. - “Normal” Django app: All other Django apps that you create explicitly with
python manage.py startapp <appname>
have the same structure. These apps contain a specific functional part of your project. These apps are portable (or “pluggable”), which means you can copy the folder and paste it in a new and different Django project that you created elsewhere. Then you need to do the steps described above to connect it within your new Django project.
- Management app: The first Django app that gets created when you set up the project is a bit different than subsequent apps. I call this one the “management app” because it contains e.g. the
Does that make sense and correspond with your understanding @sndselecta?
Become a Member to join the conversation.
reblark on Oct. 31, 2019
Is this “universal” templates folder hidden?