
Question:
I'm stuck due to <a href="https://stackoverflow.com/questions/8618611/serving-django-static-files-in-development-envirnoment" rel="nofollow">an</a> <a href="https://stackoverflow.com/questions/5602263/serving-static-files-for-development-mode-in-django" rel="nofollow">evergreen</a> <a href="https://stackoverflow.com/questions/10806287/serving-static-files-in-django-development" rel="nofollow">issue</a>, static files not served. Conversely the files placed in the MEDIA_ROOT
subtree get served correctly under MEDIA_URL
.
Stripped settings.py
:
DEBUG = True
STATIC_URL = '/static/'
STATIC_ROOT = '/home/foo/devel/static'
MEDIA_URL = '/media/'
MEDIA_ROOT = '/home/foo/devel/media'
# the following is deprecated but is it seems grappelly requires it
ADMIN_MEDIA_PREFIX = STATIC_URL + "grappelli/"
STATIC_FILES = ()
STATICFILES_FINDERS = (
'django.contrib.staticfiles.finders.FileSystemFinder',
'django.contrib.staticfiles.finders.AppDirectoriesFinder',
)
To create the project I did:
$ cd /home/foo/devel/
$ virtualenv testdrive
$ . bin/activate; pip install django; cd testdrive
$ django-admin.py fbtest
and got this directory tree (stripped):
. <-- /home/foo/devel/
├── bin
├── fbtest
│ └── fbtest
│ ├── media
│ │ └── foo.jpg
│ ├── static
│ └────── foo.jpg
├── include
└── lib
Files under STATIC_URL
should be served automatically by Django staticfiles (not in my case), while other files have to be handled manually. So I appended these lines to urls.py
:
import settings
if settings.DEBUG:
urlpatterns += patterns('',
url(r'^%s(?P<path>.*)$' % settings.MEDIA_URL.lstrip("/"),
'django.views.static.serve', {
'document_root': settings.MEDIA_ROOT,
}),
)
Accessing http://host/media/filebrowser/foo.jpg
works, while http://host/static/foo.jpg
gives error 404. Why?
<blockquote>
Files under STATIC_URL
should be served automatically by Django staticfiles (not in my case), while other files have to be handled manually.
That's incorrect. Django never serves STATIC_ROOT
ever -- not even in development. What it <em>does</em> do is make files in each app's "static" directory and files in any directory specified in STATICFILES_DIRS
available at STATIC_URL
. You don't actually manually put anything in STATIC_ROOT
ever; in fact, in development, you shouldn't even have the directory there. Put simply, STATIC_ROOT
is only a dumping ground for your static files <em>in production</em> when you run the collectstatic
management command.
In development, all static files should go into someapp/static
, where "someapp" is the app they apply to. In the case that the files apply to the project as a whole, a global CSS file for example, you need to create an entirely different directory (i.e. <em>not</em> the same as STATIC_ROOT
or MEDIA_ROOT
) and then add that directory to STATICFILES_DIRS
. For example, I normally call mine "assets", so:
STATICFILES_DIRS = (
os.path.join(os.path.dirname(__file__), 'assets'),
)
Answer2:It was a silly error. I forgot to add fbtest
to INSTALLED_APPS
, so the static file machinery didn't manage static files for this app.
This problem is realy evergreen... Some hints:
TEMPLATE_CONTEXT_PROCESSORS = (
# ...
'django.core.context_processors.static',
# ...
)
INSTALLED_APPS = (
# ...
'django.contrib.staticfiles',
# ...
)
<ul><li>Did you use? <a href="https://docs.djangoproject.com/en/dev/ref/contrib/staticfiles/#django-admin-collectstatic" rel="nofollow">django-admin-collectstatic</a> command?</li>
<li>Can you help add <a href="https://docs.djangoproject.com/en/dev/howto/static-files/#django.views.static.serve" rel="nofollow">show_indexes=True</a> in url settings?</li>
<li>Some symbolic link?</li>
<li>Run app with --adminmedia=../grappelli/static/grappelli arg.?</li>
</ul>My settings for django 1.4 (no grappelli):
urls.py
if settings.DEBUG:
urlpatterns = patterns('',
url(r'^%s(?P<path>.*)$' % settings.STATIC_URL.lstrip('/'), 'django.views.static.serve',
{'document_root': settings.STATIC_ROOT, "show_indexes": True}),
url(r'^%s(?P<path>.*)$' % settings.MEDIA_URL.lstrip('/'), 'django.views.static.serve',
{'document_root': settings.MEDIA_ROOT, "show_indexes": True}),
) + urlpatterns
settings.py
MEDIA_ROOT = os.path.join(PROJECT_DIR, 'media')
STATIC_ROOT = os.path.join(PROJECT_DIR, 'static')
MEDIA_URL = '/media/'
STATIC_URL = '/static/'
ADMIN_MEDIA_PREFIX = '/static/admin/'
TEMPLATE_CONTEXT_PROCESSORS = (
# ...
'django.core.context_processors.static',
# ...
)
INSTALLED_APPS = (
# ...
# 'django.contrib.staticfiles',
# ...
)