How to Serve static Media Files in Django? - django

I'm beginner with Web Server Apache. I want to ask your guys how to Serve Media Files in Django.
I read this: https://docs.djangoproject.com/en/2.0/howto/deployment/wsgi/modwsgi/#serving-files
This example sets up Django at the site root, but serves robots.txt, favicon.ico, and anything in the /static/ and /media/ URL space as a static file. All other URLs will be served using mod_wsgi:
Alias /robots.txt /path/to/mysite.com/static/robots.txt
Alias /favicon.ico /path/to/mysite.com/static/favicon.ico
Alias /media/ /path/to/mysite.com/media/
Alias /static/ /path/to/mysite.com/static/
<Directory /path/to/mysite.com/static>
Require all granted
</Directory>
<Directory /path/to/mysite.com/media>
Require all granted
</Directory>
WSGIScriptAlias / /path/to/mysite.com/mysite/wsgi.py
<Directory /path/to/mysite.com/mysite>
<Files wsgi.py>
Require all granted
</Files>
</Directory>
If you are using a version of Apache older than 2.4, replace Require all granted with Allow from all and also add the line Order deny,allow above it.
I ask Web Server supporter, they said my server have supported mode mod_wsgi already and they said to me that I can config it in .htaccess. But I really have no knowledge about this. Please help me rewrite URL:
Rewrite URL mydomain.com/served/ to folder with path /home/mydomain.com/public_html/media. All files in /home/mydomain.com/public_html/media/filename.jpg will access with mydomain.com/served/

You should just be able to use the Alias directive to alias /served/ to the media folder in question. So for example:
Alias /served/ /home/example.com/public_html/media/
That would mean that a request to http://example.com/served/filename.jpg will map through to /home/example.com/public_html/media/filename.jpg. You can do a similar thing for resources in /static/.
(Note that the example above uses example.com rather than mydomain.com due to SO restrictions.)

Related

Uploading files show permission denied (CentOS7 + Apache + mod_wsgi + django)

I deployed a beta version of my django app to DigitalOcean and I am serving it using Apache and WSGI.
Everything works well include static files and 'get' media files(I saved it directly to DB), except uploading files.
It shows 'Permission denied' error, with full directory like '/home/test/project/media/test.jpeg'.
I configured httpd-vhosts like this.
<VirtualHost *:80>
ServerName example.com
ServerAlias www.example.com
WSGIScriptAlias / /home/test/project/project/wsgi.py
WSGIDaemonProcess example.com python-home=/home/test/project/.venv python-path=/home/test/project/project
WSGIProcessGroup example.com
Alias /static/ /home/test/project/frontend/build/static/ # react build dir
<Directory /home/test/project/frontend/build/static>
Require all granted
</Directory>
Alias /uploadImg/ /home/test/project/media/
<Directory /home/test/project/media>
Require all granted
</Directory>
<Directory /home/test/project/project>
<Files wsgi.py>
Require all granted
</Files>
</Directory>
</VirtualHost>
So httpd is running with daemon, and my directory 'media' is owned by root, 755.
But the directory 'media' is symbolic link dir which located at '/home/test/'
I did many attempts to fix it but nothing works..
Thanks for all the responses
I solved it myself.
My problem was about 'who runs the apache process' and 'who owned the dir'.
It should be same user or group with writing authority.
Hope someone who have problem with this was helpful.

Django Apache DocumentRoot?

What directory must the DocumentRoot in Apache be set to run a Django app is it the static directory but that does not work? Thanks to all for the help in advance.
You point to project root; where wsgi.py file is. From documentation:
WSGIScriptAlias / /path/to/mysite.com/mysite/wsgi.py
WSGIPythonHome /path/to/venv
WSGIPythonPath /path/to/mysite.com
<Directory /path/to/mysite.com/mysite>
<Files wsgi.py>
Require all granted
</Files>
</Directory>
Static file are configured separately. Details here. Example (again, from docs):
Alias /robots.txt /path/to/mysite.com/static/robots.txt
Alias /favicon.ico /path/to/mysite.com/static/favicon.ico
Alias /media/ /path/to/mysite.com/media/
Alias /static/ /path/to/mysite.com/static/
<Directory /path/to/mysite.com/static>
Require all granted
</Directory>
<Directory /path/to/mysite.com/media>
Require all granted
</Directory>
WSGIScriptAlias / /path/to/mysite.com/mysite/wsgi.py
<Directory /path/to/mysite.com/mysite>
<Files wsgi.py>
Require all granted
</Files>
</Directory>
When using Django, the DocumentRoot directive is not needed.
Under the traditional approach to web sites, where Apache serves pre-written HTML files, Apache uses DocumentRoot, say
DocumentRoot = /var/www/website
so that when a user request a resource like users/profile.html, it can map that to the filesystem file /var/www/website/users/profile.html, which is an actual file.
In Django, by contrast, there are no pre-written HTML files for Apache to find. Instead, all requests are directed to Django directly, which constructs the HTML file dynamically and returns that. Thus, Apache doesn't need a DocumentRoot, it needs to know the location of Django's WSGI application file wsgi.py, which is the "gateway" for sending HTTP requests to Django so that it can construct the right HTML file to return. This is specifed by the WSGIScriptAlias directive and associated Apache configuration; e.g.
WSGIScriptAlias / /path/to/mysite.com/mysite/wsgi.py
<Directory /path/to/mysite.com/mysite>
<Files wsgi.py>
Require all granted
</Files>
</Directory>
as given by the Django documentation on deploying Django with Apache.
TL;DR: You don't need DocumentRoot, you need WSGIScriptAlias for Django.
I think you are asking for this:
ServerAdmin example#localhost
DocumentRoot /var/www/html

How to serve static index with Apache and mod_wsgi

So I'm using Apache and mod_wsgi to serve a django webapp. My client is a single-page application, which talks to the django back-end. Since the actual index is a static html file, I would like it so that when my user navigates to '/', then Apache serves them my static index.html, but when they visit '/foo/' or '/bar/', then they get dynamic content from the django backend.
Relevant apache conf:
Alias /static /path/to/static
<Directory /path/to/static>
Require all granted
</Directory>
<Directory /path/to/django/site>
<Files wsgi.py>
Require all granted
</Files>
</Directory>
WSGIDaemonProcess sitename python-home=/path/to/env python-path=/path/to/django
WSGIProcessGroup sitename
WSGIScriptAlias / /path/to/sitename/wsgi.py
WSGIPassAuthorization On
However, if I try to Alias / /path/to/static/ then django doesn't get to do its thing, since it clashes with WSGIScriptAlias / /path/to/sitename/wsgi.py. Is there any way to make Apache serve a static file in what would otherwise be django's namespace?
Try:
WSGIScriptAliasMatch ^/(foo|bar)/ /path/to/sitename/wsgi.py/$1/
WSGIApplicationGroup %{GLOBAL}
The second directive is just to make sure it doesn't create separate instances of the application for each matched prefix. It shouldn't, but this just makes sure and is generally a good idea to use that directive anyway for various reasons.

Configure Apache to override WSGI

I have a Django based site served by Apache2. My virtualhost is configured so that my domain (call it example.com) serves my wsgi application.
I would also like to serve a Wordpress site at example.com/blog using Apache. How would I serve the Wordpress site at /blog using Apache? Currently, my request gets captured by Django and I get a 404 since /blog is not in my Django urls.
In the Django docs (https://docs.djangoproject.com/en/1.9/howto/deployment/wsgi/modwsgi/) they give this example:
Alias /media/ /path/to/mysite.com/media/
Alias /static/ /path/to/mysite.com/static/
<Directory /path/to/mysite.com/static>
Require all granted
</Directory>
<Directory /path/to/mysite.com/media>
Require all granted
</Directory>
WSGIScriptAlias / /path/to/mysite.com/mysite/wsgi.py
<Directory /path/to/mysite.com/mysite>
<Files wsgi.py>
Require all granted
</Files>
</Directory>
This is for static files, but would work for your blog too.
Your problem is that you don't recognize the blog reference until you are in the Django URL router. Although you can do a URL-rule + view to do a redirect, the easiest way to do this is create a new subdomain, e.g. blog.mydomain.com, and configure Apache to handle the additional site. I do this for all of my Django sites and it works fine.
In your Apache conf add these lines to your VirtualHost:
Alias /blog /var/www/example.com/blog/
<Directory /var/www/example.com/blog>
Require all granted
</Directory>

Location of settings file for deploying static files with Django on Apache2 with mod_wsgi

I am trying to follow the tutorial on Deploying static files on Apache using mod_wsgi from the 1.6 Documentation. I already have a work in progress site deployed on Apache using mod_wsgi but I need to learn how to correctly deploy static files instead of linking to external Bootstrap CSS as I have been doing.
My issue is I have no idea where the below sample settings from the documentation is or where it should go.
Below is the relevant DjangoProject text
If, however, you have no option but to serve media files on the same
Apache VirtualHost as Django, you can set up Apache to serve some URLs
as static media, and others using the mod_wsgi interface to Django.
This example sets up Django at the site root, but explicitly serves
robots.txt, favicon.ico, any CSS file, and anything in the /static/
and /media/ URL space as a static file. All other URLs will be served
using mod_wsgi:
It then gives the below sample code which I will need to modify
Alias /robots.txt /path/to/mysite.com/static/robots.txt
Alias /favicon.ico /path/to/mysite.com/static/favicon.ico
AliasMatch ^/([^/]*\.css) /path/to/mysite.com/static/styles/$1
Alias /media/ /path/to/mysite.com/media/
Alias /static/ /path/to/mysite.com/static/
<Directory /path/to/mysite.com/static>
Require all granted
</Directory>
<Directory /path/to/mysite.com/media>
Require all granted
</Directory>
WSGIScriptAlias / /path/to/mysite.com/mysite/wsgi.py
<Directory /path/to/mysite.com/mysite>
<Files wsgi.py>
Require all granted
</Files>
</Directory>
Followed by some clarification instruction
If you are using a version of Apache older than 2.4, replace Require
all granted with Allow from all and also add the line Order deny,allow
above it.
There are some similarities to my below <VirtualHost> file. Should I just add it to this? Or should it be stored in another location?
<VirtualHost *:80>
ServerName phaedrus.scss.tcd.ie/bias_experiment
ServerAlias phaedrus.scss.tcd.ie
WSGIScriptAlias /bias_experiment/ /var/www/bias_experiment/src/bias_experiment/index.wsgi
Alias /static/ /var/www/bias_experiment/src/bias_experiment/static/
<Location "/static/">
Options -Indexes
</Location>
</VirtualHost>
Any help would be great.
Yes, this is supposed to go in the same place as your virtualhost configuration.