Django’s handling of static files is great, but sometimes causes confusion. If you’re wondering how it all fits together, what some of the settings mean, or just want some example uses, then keep reading.
Introduction
A typical Django project will have multiple sets of static files. The two common sources are applications with a static
directory for media specific to them, and a similarly-named directory somewhere in the project for media tying the whole project together.
Ultimately, you want these all to end up in one place, to be served to the end user. This is where the collectstatic
command comes in; as the name suggests, it’ll collect all your static files together into that one place. Of course, if you have DEBUG
set to True
in your settings, runserver
will happily handle all this for you, but that won’t be the case for your final deployment (and nor should it be!)
So how does this all happen?
Configuration
Finders
First of all, where to find the static files?
By default settings.py
will be created with a STATICFILES_FINDERS
setting, with a value of:
These will be used to find the source static files. The AppDirectoriesFinder
is responsible for picking up $app_name/static/
, the FileSystemFinder
uses the directories specified in the STATICFILES_DIRS
tuple.
You’ll probably want STATICFILES_DIRS
to look something like the below:
Storage
The STATICFILES_STORAGE
setting controls how the files are aggregated together. The default value is django.contrib.staticfiles.storage.StaticFilesStorage
which will copy the collected files to the directory specified by STATIC_ROOT
.
Do not confuse STATIC_ROOT
, to where static files are collected, with the aforementioned STATICFILES_DIRS
; the former is output, the latter are inputs. They should not overlap. This is a common mistake.
Update: To be absolutely clear, STATIC_ROOT
should live outside of your Django project - it’s the directory to where your static files are collected, for use by a local webserver or similar; Django’s involvement with that directory should end once your static files have been collected there
URL
Last but not least, STATIC_URL
should be the URL at which a user / client / browser can reach the static files that have been aggregated by collectstatic
.
If you’re using the default StaticFilesStorage
, then this will be the location of where your nginx
(or similar) instance is serving up STATIC_ROOT
, e.g. the default /static/
, or, better, something like http://static.example.com/
. If you’re using Amazon S3 this will be http://your_s3_bucket.s3.amazonaws.com/
. Essentially, this is wholly dependent on whatever technique you’re using to host your static files. It’s a URL, and not a file path
Common Mistakes
- Overlap between
STATICFILES_DIRS
andSTATIC_ROOT
- the former is a set of places to look for static files, the latter is where they’re stored - Incorrect
STATIC_URL
- it’s a URL, not a file path - Incorrect configuration of whatever you’re using to host your static content; this is why I use S3, in my experience it’s the least effort to get working
- Having
STATIC_ROOT
inside your project directory. While not strictly a mistake, it’s not where it belongs, and is generally a sign of other misunderstandings
Examples
All of these will assume you’ve left STATICFILES_FINDERS
as its default, and STATICFILES_DIRS
as described above; I’ve never yet had a reason, across dozens of projects, for these not to be the case
Apache serving static files
Apache config (e.g. /etc/apache2/sites-enabled/com.example.static.conf
):
Amazon S3
(Update: If you want more information on this topic, check out my follow-up blog post, Using Amazon S3 to host your Django Static Files)
Note this uses django-storages
, which is a nice wide-ranging collection of custom backends for STATICFILES_STORAGE
described above.
I frequently deploy to Heroku where custom httpd configuration is nontrivial, so often use this method.
Conclusion
Static file handling is important to get right, and straight forward once you know how, but easy to get wrong. I hope this clarifies things.
As ever, drop me a line if you have any queries, questions or complaints.
Did this help? Check out my book
Ok so I'm still writing the book so you can't buy it just yet. But if you want to make sure that you're serving your static files in the best way possible, you'll want it:
Check out the book