2
votes

I’ve played with a little Django (v2.0.1) locally. Now I am trying to implement a test case on my production Apache web server. I’m running an Ubuntu 14.04 DigitalOcean droplet (will upgrade to 18.04 later this year).

I got Django running.

Here it is: http://www.angeles4four.info:8000/

Before I log into my admin panel, I figure it’s best practices to set up HTTPS first. But when I visit that URL with https://, Chrome throws this message:

This site can’t provide a secure connection www.angeles4four.info sent an invalid response. ERR_SSL_PROTOCOL_ERROR

And my shell on my server shows this message:

[20/Jan/2018 23:54:39] "GET / HTTP/1.1" 200 16559 [21/Jan/2018 00:01:23] code 400, message Bad request syntax ('\x16\x03\x01\x00Ì\x01\x00\x00È\x03\x03&6U\x10µ\x82\x97\x7f´8\x1e«\x0e¿ÿ§\x89æ\x82\r¢G§\x01ç°P%\x80)ÕÃ\x00\x00\x1c * À+À/À,À0̨̩À\x13À\x14\x00\x9c\x00\x9d\x00/\x005\x00') [21/Jan/2018 00:01:23] You're accessing the development server over HTTPS, but it only supports HTTP.

That’s because SSL isn’t set up. My current SSL Certificate Authority is Let’s Encrypt. SSL is running properly for my public_html content but not for my recent deployment of Django.

I found some resources elsewhere on SO for setting up SSL with Django.

In an SO post titled, “Configure SSL Certificate on Apache for Django Application (mod_wsgi)”, a highly upvoted answer by Alexey Kuleshevich suggests a template for 000-default.conf and default-ssl.conf for Apache vhosts. See here: Configure SSL Certificate on Apache for Django Application (mod_wsgi)

I did my best to change up the suggested values and entries so that they refer to my specific configuration. Here are what these two vhost configuration files of mine look like now.

/etc/apache2/sites-available/angeles4four.info-le-ssl.conf:

<IfModule mod_ssl.c> 
<VirtualHost *:443>
        #ServerName www.example.com
        ServerAdmin [email protected]
        ServerName angeles4four.info
        ServerAlias www.angeles4four.info
        DocumentRoot /var/www/html/angeles4four.info/public_html

        ErrorLog ${APACHE_LOG_DIR}/error.log
        CustomLog ${APACHE_LOG_DIR}/access.log combined

        # Django Application
        Alias /static /var/www/html/angeles4four.info/public_html/Cel2FahConversion
        <Directory /var/www/html/angeles4four.info/public_html/Cel2FahConversion>
                Require all granted
        </Directory>
        <Directory /var/www/html/angeles4four.info/public_html/Cel2FahConversion>
                <Files wsgi.py>
                        Require all granted
                </Files>
        </Directory>
        WGIDaemonProcess cel python-path=/var/www/html/angeles4four.info/public_html/Cel2FahConversion/venv/bin/python3
        WSGIProcessGroup cel
        WSGIScriptAlias / /var/www/html/angeles4four.info/public_html/Cel2FahConversion/Cel2FahConversion/Cel2FahConversion/wsgi.py

        SSLCertificateFile /etc/letsencrypt/live/angeles4four.info/cert.pem
        SSLCertificateKeyFile /etc/letsencrypt/live/angeles4four.info/privkey.pem
        Include /etc/letsencrypt/options-ssl-apache.conf
        SSLCertificateChainFile /etc/letsencrypt/live/angeles4four.info/chain.pem
</VirtualHost>
</IfModule>

angeles4four.info.conf:

<VirtualHost *:80>

        #ServerName www.example.com
        ServerAdmin [email protected]
        ServerName angeles4four.info
        ServerAlias www.angeles4four.info
        DocumentRoot /var/www/html/angeles4four.info/public_html
        <Directory "/var/www/html/angeles4four.info/public_html">
                Options Indexes FollowSymlinks
                AllowOverride All
                Require all granted
        </Directory>

        ErrorLog ${APACHE_LOG_DIR}/error.log
        CustomLog ${APACHE_LOG_DIR}/access.log combined

RewriteEngine on
RewriteCond %{SERVER_NAME} =angeles4four.info [OR]
RewriteCond %{SERVER_NAME} =www.angeles4four.info
RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent]
</VirtualHost>

No dice. I still get the same traceback as I initially shared.

The next SO post I came across suggests modifying settings.py. Here it is: Error "You're accessing the development server over HTTPS, but it only supports HTTP"

The upvoted suggestion here by YoYo is to modify session cookies and secure SSL redirect. YoYo also recommends managing base, local, production settings which doesn’t really apply to me. So I tried adding these three lines to my settings.py:

SESSION_COOKIE_SECURE = True
CSRF_COOKIE_SECURE = True
SECURE_SSL_REDIRECT = True

My python3 manage.py runserver shell traceback still says: “You're accessing the development server over HTTPS, but it only supports HTTP.

Any ideas? What else could I try?

Thanks for your attention.

One final note: This is among first SO posts which is why my hyperlinks are pasted as raw text. Once I get some upvotes, I’ll be sure to return here to edit this post and by polishing my links with anchor markup.

1
You shouldn't even be running python3 manage.py runserver when using mod_wsgi to host Django. Why are you still running it? What happens when you don't run it and actually access the host:port for Apache?Graham Dumpleton
The reason why I was running Django using 'python3 manage.py runserver' instead of wsgi is because I am a rookie with deploying Django. With the mod_wsgi keyword I have found a helpful DigitalOcean guide and official Django docs. I'll play around with them and return here soon to report my solution.Angeles89

1 Answers

3
votes

My solution was to restart the Django configuration over on a new domain.

Here it is running: https://daniel496.agency/

I didn’t realize that Django was suppose to be run using wsgi. I was just foolishly running the server with $ python manage.py runserver 0.0.0.0:8000 like when I was testing locally when I was coding my app. The keyword here (courtesy of Graham Dumpleton, is mod_wsgi). So I found a guide called, “How To Serve Django Applications with Apache and mod_wsgi on Ubuntu 14.04”.

This guide helped enormously too: Configure SSL Certificate on Apache for Django Application (mod_wsgi)

On my road to serving Django "properly" I encountered an issue where it was timing out and resolved to this error message:

Internal Server Error

The server encountered an internal error or misconfiguration and was unable to complete your request. Please contact the server administrator at [email protected] to inform them of the time this error occurred, and the actions you performed just before this error. More information about this error may be available in the server error log.

Apache/2.4.7 (Ubuntu) Serverat www.daniel496.agency Port 443

Here the issue was with libapache2-mod-wsgi. Apparently this package is written for Python2 and the Django 2.0 that I am running is Python3. So the solution was to install the ‘libapache2-mod-wsgi-py3’ package in the official Ubuntu repos (lucky for me it is included in 14.04).

For what it’s worth, here are my working configuration files.

daniel496.agency-le-ssl.conf:

<IfModule mod_ssl.c>
<VirtualHost *:443>

        ServerAdmin [email protected]
        ServerName daniel496.agency
        ServerAlias www.daniel496.agency
        DocumentRoot /var/www/html/daniel496.agency/public_html

        ErrorLog ${APACHE_LOG_DIR}/error.log
        CustomLog ${APACHE_LOG_DIR}/access.log combined

        # Django project
        Alias /static /home/<user>/cel2fah/static
        <Directory /home/<user>/cel2fah/static>
                Require all granted
        </Directory>

        <Directory /home/<user>/cel2fah/cel2fah>
                <Files wsgi.py>
                    Require all granted
                </Files>
        </Directory>

        WSGIDaemonProcess cel2fah2 python-path=/home/<user>/cel2fah python-home=/home/<user>/cel2fah/venv
        WSGIProcessGroup cel2fah2
        WSGIScriptAlias / /home/<user>/cel2fah/cel2fah/wsgi.py

Include /etc/letsencrypt/options-ssl-apache.conf
SSLCertificateFile /etc/letsencrypt/live/daniel496.agency/cert.pem
SSLCertificateKeyFile /etc/letsencrypt/live/daniel496.agency/privkey.pem
SSLCertificateChainFile /etc/letsencrypt/live/daniel496.agency/chain.pem

</VirtualHost>
</IfModule>

And daniel496.agency.conf:

<VirtualHost *:80>
        ServerAdmin [email protected]
        ServerName daniel496.agency
        ServerAlias www.daniel496.agency
        DocumentRoot /var/www/html/daniel496.agency/public_html

        ErrorLog ${APACHE_LOG_DIR}/error.log
        CustomLog ${APACHE_LOG_DIR}/access.log combined
<IfDefine IgnoreBlockComment>
        Alias /static /home/<user>/cel2fah/static
        <Directory /home/<user>/cel2fah/static>
                Require all granted
        </Directory>

        <Directory /home/<user>/cel2fah/cel2fah>
                <Files wsgi.py>
                    Require all granted
                </Files>
        </Directory>

#       WSGIDaemonProcess cel2fah2 python-path=/home/<user>/cel2fah python-home=/home/<user>/cel2fah/venv
 #      WSGIProcessGroup cel2fah2
#       WSGIScriptAlias / /home/<user>/cel2fah/cel2fah/wsgi.py
</IfDefine>
        RewriteEngine on
        RewriteCond %{SERVER_NAME} =daniel496.agency [OR]
        RewriteCond %{SERVER_NAME} =www.daniel496.agency
        RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent]
</VirtualHost>

I found all sorts of new, detailed resources for further reading on the Read the Docs to help configure Django with better practices such as putting my wsgi scripts inside /usr/local/www/wsgi-scripts/ instead of in my project folder in my home directory.