Skip to content

Instantly share code, notes, and snippets.

@hcosta
Last active August 18, 2022 17:31
Show Gist options
  • Save hcosta/0ba330db8fd15eb12e69196e76034f10 to your computer and use it in GitHub Desktop.
Save hcosta/0ba330db8fd15eb12e69196e76034f10 to your computer and use it in GitHub Desktop.
Desplegar Django en doplet Ubuntu 16.04 de Digital Ocean

Actualizamos el repositorio como root (lo indico con $)

$ add-apt-repository universe
$ apt-get update
$ apt-get upgrade

Instalamos las dependencias y python, que por defecto viene en la versión 2.7

$ apt-get install python3 nginx supervisor # postgresql postgresql-contrib (si no se quiere sqlite)

En este punto tendremos que instalar pip y pip3 para facilitarnos la vida

$ apt-get install python-pip python3-pip

Instalamos virtualenvwrapper en python 2.7

$ pip install virtualenvwrapper

También podemos actualizar pip

$ pip install --upgrade pip
$ pip3 install --upgrade pip

Ahora deberemos contar con un usuario no root, seguir esta guía para añdirlo:

https://www.digitalocean.com/community/tutorials/configuracion-inicial-del-servidor-en-ubuntu-16-04-es

$ adduser hektor
$ usermod -aG sudo hektor

Cambiamos al nuevo usuario

$ su hektor

Creamos un directorio para almacenar entornos virtuales

mkdir ~/.environments

Editamos el fichero ~/.bashrc y añadimos al final los directorios de virtualenvwrapper

nano ~/.bashrc
export WORKON_HOME=~/.environments
source /usr/local/bin/virtualenvwrapper.sh

Después de guardar los cambios recargaremos la configuración de usuario

source ~/.bashrc

Ahora podemos crear nuestro entorno virtual (en mi caso 'hektorprofe') utilizando python3

mkvirtualenv hektorprofe --python=$(which python3)

Cambiamos al entorno virtual, aunque ya deberíamos estar en él

workon hektorprofe

Creamos un directorio para almacenar nuestro proyecto

(hektorprofe) mkdir ~/hektorprofe.net
(hektorprofe) cd ~/hektorprofe.net

Ya podemos clonar el proyecto que tengamos en git o donde sea

(hektorprofe) git clone https://github.com/hcosta/hektorprofe.net.git

Instalamos las dependencias (si tenemos un requirements.txt)

(hektorprofe) pip install -r requirements.txt

Migramos la base de datos, por si hace falta

(hektorprofe) python manage.py migrate

Instalamos gunicorn dentro del entorno virtual (no sirve instalado con apt-get, desinstalarlo)

(hektorprofe) pip install gunicorn

Probamos si lanza el proyecto desde la raíz donde está el manage.py (no da error)

(hektorprofe) gunicorn hektorprofe.wsgi:application --bind=127.0.0.1:8000

Cambiamos de nuevo a root

(hektorprofe) su root

Ahora configuramos supervisr (que funciona con python 2.7) y mantendrá nuestro proyecto en marcha

$ touch /etc/supervisor/conf.d/hektorprofe.conf

Editamos su configuración

$ nano /etc/supervisor/conf.d/hektorprofe.conf
[program:hektorprofe]
user = root
directory = /home/hektor/hektorprofe.net/hektorprofe
command = /home/hektor/.environments/hektorprofe/bin/python /home/hektor/.environments/hektorprofe/bin/gunicorn hektorprofe.wsgi:application
stdout_logfile = /home/hektor/hektorprofe.net/logs/gunicorn_supervisor.log
redirect_stderr = true

Una vez guardada la configuración creamos la carpeta logs

mkdir -p /home/hektor/hektorprofe.net/logs

Ahora le decimos a supervisor que actualice las configuraciones

$ supervisorctl reread
$ supervisorctl update

Con los siguientes comandos podemos manejar la aplicación

$ supervisorctl status hektorprofe                       
$ supervisorctl stop hektorprofe  
$ supervisorctl restart hektorprofe 
$ supervisorctl start hektorprofe

Creamos una configuración básica para nginx, el servidor

$ nano /etc/nginx/sites-available/hektorprofe.conf
server {
        listen 80;
        server_name hektorprofe.net;  # <-- esta configuración redirecciona todo de hektorprofe.net a www.hektorprofe.net
        return 301 https://www.hektorprofe.net$request_uri;  # <-- tampoco hace falta redireccionar a https si no se usan certificados
}

server {
        
        # cambiar por listen 80; si no se utilizan certificados SSL
        listen 443 ssl;  
        server_name www.hektorprofe.net; 

        access_log /home/hektor/hektorprofe.net/logs/nginx.access.log;
        error_log  /home/hektor/hektorprofe.net/logs/nginx.error.log;

        # Desactivar las siguientes tres líneas si no se utilizan certificados para https, más abajo explico cómo crearlos
        ssl on;
        ssl_certificate /etc/letsencrypt/live/hektorprofe.net/fullchain.pem;
        ssl_certificate_key /etc/letsencrypt/live/hektorprofe.net/privkey.pem;

        location /static/ {
            alias /home/hektor/hektorprofe.net/hektorprofe/static/;
        }

        location /media/ {
            alias /home/hektor/hektorprofe.net/hektorprofe/media/;
        }

        location = /favicon.ico {
            alias /home/hektor/hektorprofe.net/hektorprofe/static/favicon.ico;
        }

        location / {
            proxy_pass http://127.0.0.1:8000;  # <-- En este puerto se inicia Gunicorn por defecto
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        }

}

Guardamos y creamos un enlace simbólico en sites-enabled

$ cd /etc/nginx/sites-enabled
$ sudo ln -s ../sites-available/hektorprofe.conf

Reiniciamos nginx

$ service nginx restart

Cómo crear un certificado SSL

https://www.linode.com/docs/security/ssl/install-lets-encrypt-to-create-ssl-certificates/

$ git clone https://github.com/letsencrypt/letsencrypt /opt/letsencrypt
$ cd /opt/letsencrypt
$ service nginx stop
$ ./letsencrypt-auto certonly --standalone --renew-by-default -d hektorprofe.net -d www.hektorprofe.net -d static.hektorprofe.net
$ service nginx start

No olvidar renovarlos cada 3 meses

$ service nginx stop
$ cd /opt/letsencrypt
$ sudo -H ./letsencrypt-auto certonly --standalone --renew-by-default -d hektorprofe.net -d www.hektorprofe.net
$ service nginx start

Otras consideraciones en settings.py

  • DEBUG = False
  • ALLOWED_HOSTS = ['127.0.0.1', 'hektorprofe.net', 'www.hektorprofe.net']
  • STATIC_ROOT = os.path.join(BASE_DIR, 'static') + python manage.py collectstatic
  • SECURE_SSL_REDIRECT = False # <-- se hace a nivel de nginx, no lo queremos automático

Reinicio rápido

$ supervisorctl restart hektorprofe  # <-- Para Django
$ service nginx restart  # <--- Para Nginx
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment