Despliegue de Django con gunicornio y nginx


Answers

No soy un gurú de implementación, pero compartiré algunas de mis prácticas para implementar Django con gevent (aunque debería ser similar a gunicorn).

virtualenv es genial por razones que no entraré. Sin embargo, encontré que virtualenv-wrapper ( docs ) es muy útil, especialmente cuando trabajas en muchos proyectos, ya que permite cambiar fácilmente entre los diferentes virtualenvs. Esto realmente no se aplica al entorno de despliegue; sin embargo, cuando necesito solucionar problemas en el servidor usando SSH, esto me pareció muy útil. Otra ventaja de usarlo es que administra el directorio virtualenv, por lo tanto, menos trabajo manual para usted. Los Virtualenvs están destinados a ser desechables, de modo que en caso de que tenga problemas de versión o cualquier otro problema de instalación, puede simplemente volcar el entorno y crear uno nuevo. Como resultado, es una buena práctica no incluir ninguno de los códigos de su proyecto dentro del virtualenv. Debe mantenerse separado.

En cuanto a la configuración de múltiples sitios, virtualenv es más o menos la respuesta. Debe tener un virutalenv por separado para cada proyecto. Solo eso puede resolver muchos problemas. Luego, cuando implemente, un proceso de Python diferente ejecutará diferentes sitios, lo que evita cualquier posible conflicto entre las implementaciones. Una herramienta que particularmente encontré muy útil en la administración de múltiples sitios en el mismo servidor es supervisor ( documentos ). Proporciona una interfaz sencilla para iniciar, detener y reiniciar diferentes instancias de Django. También es capaz de reiniciar automáticamente un proceso cuando falla o cuando la computadora se inicia. Entonces, por ejemplo, si se levanta una excepción y nada lo atrapa, todo el sitio web puede caer. El supervisor lo detectará y reiniciará automáticamente la instancia de Django. La siguiente es una configuración del programa supervisor de ejemplo (un solo proceso):

[program:foo]
command=/path/toviertualenv/bin/python deploy.py
directory=/path/where/deploy.py/is/located/
autostart=true
autorestart=true
redirect_stderr=True
user=www

Para Nginx, sé que puede ser abrumador al principio. Encontré el libro de Nginx muy útil. Explica todas las principales directivas nginx.

En mi instalación de nginx, encontré que la mejor práctica es configurar solo las configuraciones centrales en el archivo nginx.conf y luego tengo una carpeta separada de sites donde guardo las configuraciones nginx para cada uno de los sitios que tengo. Luego solo incluyo todos los archivos de esa carpeta en el archivo de configuración central. Uso la directiva include sites/+*.conf; . De esta forma, solo incluye los archivos que comienzan con el símbolo + dentro de la carpeta de sites . De esta forma, solo con el nombre de archivo puedo controlar qué archivos de configuración se cargarán. Entonces, si deseo desactivar un determinado sitio, solo tengo que cambiar el nombre del archivo de configuración y reiniciar nginx. No estoy muy seguro de lo que quiere decir con "enlace simbólico entre sitios disponibles y sitios habilitados en / etc / nginx" en su pregunta, ya que son carpetas con el nombre Apache pero cumplen tareas similares a la directiva include .

En cuanto a root directivas de root y alias , son prácticamente iguales, excepto cuando se calcula su raíz. En alias , lo que sea en la location en dropeado, mientras que en la raíz en no. Imagen de que tienes la siguiente configuración de nginx:

location /static {
    alias /some/path/;
}
location /static2 {
    root /some/other/path/;
}

Si el usuario va a estas URL, entonces nginx intentará buscar los archivos en los siguientes lugares del sistema:

/static/hello/world.pdf => /some/path/hello/world.pdf
/static2/hello/world.pdf => /some/other/path/static2/hello/world.pdf

Esta es una configuración simple para el sitio nginx:

server {
    server_name .foodomain.com;
    listen 80;

    access_log logs/foodomain.log;

    gzip                on;
    gzip_http_version   1.0;
    gzip_comp_level     2;
    gzip_proxied        any;
    gzip_min_length     1100;
    gzip_buffers        16 8k;
    gzip_types          text/plain text/html text/css application/x-javascript text/xml application/xml application/xml+rss text/javascript;

    # Some version of IE 6 don't handle compression well on some mime-types, so just disable for them
    gzip_disable "MSIE [1-6].(?!.*SV1)";

    # Set a vary header so downstream proxies don't send cached gzipped content to IE6
    gzip_vary on;

    location / {
        proxy_read_timeout      30s;
        proxy_pass              http://localhost:8000;
        proxy_set_header        Host                 $host;
        proxy_set_header        User-Agent           $http_user_agent;
        proxy_set_header        X-Real-IP            $remote_addr;
    }

    location /media {
        alias   /path/to/media/;
        expires 1y;
    }

    location /static {
        autoindex on;
        expires   1y;
        alias     /path/to/static/;
    }

     location /favicon.ico {
        alias /path/to/favicon.ico;
    }
}

Espero que esto te ayude un poco.

Question

Esta es una pregunta amplia, pero me gustaría obtener una respuesta canónica. He estado intentando implementar un sitio usando gunicorn y nginx en Django . Después de leer toneladas de tutoriales, he tenido éxito, pero no puedo estar seguro de que los pasos que seguí sean lo suficientemente buenos como para ejecutar un sitio sin problemas o tal vez haya mejores formas de hacerlo. Esa incertidumbre es molesta.

Es por eso que estoy buscando una respuesta muy detallada y bien explicada para los novatos. No quiero explicar demasiado lo que sé y lo que no sé, ya que esto podría sesgar un poco las respuestas y otras personas podrían beneficiarse en menor grado de sus respuestas. Sin embargo, algunas cosas que me gustaría ver mencionadas son:

  • ¿Qué "configuración" has visto que funciona mejor? Usé virtualenv y moví mi proyecto Django dentro de este entorno, sin embargo, he visto otras configuraciones donde hay una carpeta para entornos virtuales y otra para proyectos.

  • ¿Cómo puedo configurar las cosas de una manera que permita alojar varios sitios en un único servidor?

  • ¿Por qué algunas personas sugieren usar gunicorn_django -b 0.0.0.0:8000 y otros sugieren gunicorn_django -b 127.0.0.1:8000 ? Probé esta última en una instancia de Amazon EC2 pero no funcionó mientras que la primera funcionó sin problemas.

  • ¿Cuál es la lógica detrás del archivo de configuración de nginx? Hay tantos tutoriales que usan archivos de configuración drásticamente diferentes que estoy confundido sobre cuál es mejor. Por ejemplo, algunas personas usan alias /path/to/static/folder y otras root /path/to/static/folder . Tal vez puedas compartir tu archivo de configuración preferido.

  • ¿Por qué creamos un enlace simbólico entre site-available y sites-enabled en /etc/nginx ?

  • Algunas de las mejores prácticas son como siempre bienvenidas :-)

Gracias