Cómo instalar una aplicación Django en OpenShift

OpenShift es la plataforma PaaS de Red Hat. Aunque este post trata sobre consejos y experiencia de instalar una app de Django, hay que decir que OpenShift está actualmente montado sobre Amazon Web Services y que utiliza el concepto de recurso (gear o cartucho).  Un «cartucho» puede ser una aplicación web, una base de datos MySql, una instancia de memcached, etc. La cuenta gratuita permite tener 3 cartuchos. La idea es que si tu solución necesita escalar, fácilmente se puede añadir nuevos cartuchos bajo demanda.

Aquí os presento algunos tips o problemas con los que me he encontrado:

  • Lo primero es instalar el toolkit de OpenShift, rhc. Se trata de un script Ruby con el que se puede crear aplicaciones, ver logs, acceder via SSH etc. Se instala con «gem install rhc». A mi me dio un error al instalar parte de la documentación pero funciona sin problemas.
  • La primera vez que se ejecuta rhc nos pedirá los credenciales de OpenShift (login/password) y permite crear y subir una clave pública de SSH para acceder sin tener que recordar clave alguna.
  • Para acceder vía SSH, ejecutamos «rhc ssh <app>«. Esto llama a SSH utilizando la clave pública. Como usuario, se utiliza un string-ID bastante largo. Al acceder nos situa en el «home» virtualizado: /var/lib/openshift/<UserID>. En ese directorio aparecen los componentes principales de tu aplicación. Para una aplicación Django son: app-root, git y python. La mayoria de los directorios son de sólo lectura. Solo en $HOME/app-root/data, $HOME/app-root/repo y algún que otro directorio podemos escribir.
  • Si necesitamos instalar algún componente Python, deberemos de ejecutar el script de Virtualenv. Esto se hace con «source $HOME//python/virtenv/bin/activate». Luego ya llamaos a «pip install <paquete>«.
  • En caso de tener que copiar algo vía SCP, deberemos tener cuidado de que el directorio destino tenga permiso de escritura. Esta seria una sintaxis válida «scp <fichero> <userID>@<app>-<cuenta>.rhcloud.com:/var/lib/openshift/<userID>/app-root/data«.
  • El entorno de OpenShift establece un número grande de variables de entorno que será de gran utilidad para configurar tu aplicación. Todas comienzan por «OPENSHIFT_». Por ejemplo OPENSHIFT_APP_DNS nos da el host,  OPENSHIFT_REPO_DIR el directorio donde se ubica el repositorio o OPENSHIFT_PYTHON_LOG_DIR donde se encuentran los logs de Apache.
  • El equivalente a «service httpd restart» es «ctl_app restart«. Lo utilizaremos cada vez que hagamos algún cambio en la aplicación.
  • La mejor forma de enlazar nuestra aplicación con wsgi es fijarnos en el ejemplo que viene. Apache ejecuta $HOME/app-root/repo/wsgi/application para cada request. Este script prepara el entorno de virtualenv e invoca al manejador wsgi de Django. Debemos ajustar los paths y nuestro «project.settings».
  • Lo más normal es que durante la instalación de nuestra app nos encontremos con errores tipo 500. Con «rhc tail», veremos los logs de Apache.
  • Los contenidos estáticos deben ir a $HOME/app-root/repo/wsgi/static, luego debemos configurar correctamente la variable STATIC_ROOT para que apunte al path correcto dentro de settings.py.
  • Si nuestra aplicación usa base de datos, se recomienda la ubicacion $HOME/app-root/data, ya que $HOME/app-root/repo se destina al repositorio de código.
  • Es posible tener una configuración especifica según el entorno de ejecución mirando las variables de entorno. En el ejemplo que viene por defecto, se crea una variable booleana ON_OPENSHIFT dentro settings.py que se usa para determinar la ubicación de la base de datos sqlite3.
  • Si queremos obtener la IP de aquellos que nos visitan, tenemos que usar el meta «HTTP_X_FORWARDED_FOR» en lugar «REMOTE_ADDR».
  • Por último, si queremos asociar un CNAME a nuestra app, usamos «rhc alias <app> <cname>» para crear dicho alias (imagino que añadirá un ServerAlias a la configuración de Apache).

Sin duda OpenShift es de las plataformas más económicas (o gratis) de hospedar un proyecto Django. Muy recomendable para aplicaciones inicialmente pequeñas o prototipos.