Desplegar Symfony en Web App for containers

Estos días atrás estuve trabajando en desplegar Symfony en Web App for Containers, una modalidad de App Service que te permite el despliegue de contenedores Docker, en Docker Hub, Azure Container Registry o cualquier otro repositorio privado que utilices. En este artículo te cuento cómo lo he hecho.

El código

Antes de nada, contarte que este código está basado en los ejemplos que el equipo de App Service ha puesto a nuestra disposición en GitHub. He modificado algunas cosas para adaptarlo a Symfony 3, pero he mantenido prácticamente la misma estructura que los ejemplos de nginx-fpm, con alguna modificación, que ahora te cuento:

Estructura para el contenedor de Symfony en Web App for Containers
  • local_bin: en este directorio se encuentran los archivos que se utilizarán durante el arranque del contenedor, para configurar los permisos sobre los directorios, la creación de las claves necesarias para acceder a través de SSH, además de para arrancar supervisord, que es quien ejecutará y monitorizará los procesos que necesitamos.
  • logrotate.d: son las configuraciones de la rotación de logs para nginx, php y supervisor, con el objetivo de no llenar nuestro App Service de logs innecesarios. Se utiliza logrotate para esta tarea.
  • nginx_conf: la configuración de nuestro servidor Nginx, con la que será capaz de enrutar correctamente las peticiones de Symfony 3. En el caso de que quisieras utilizar Symfony 4, deberías modificar el valor de root, ya que en la nueva versión el contenido ya no está en web sino en public, y cambiar app.php por index.php.
  • php_conf: en esta configuración estoy utilizando opcache para mejorar el rendimiento de la aplicación. También está disponible la configuración (comentada) para XDebug.
  • symfony-demo: aquí está alojada la aplicación web.
  • .gitignore: para evitar que ciertos archivos suban como parte de mi código fuente a GitHub.
  • Dockerfile: la receta para poder crear la imagen de Docker. La he modificado para eliminar la configuración de phpMyAdmin y MariaDB. Por otro lado, he añadido la instalación de composer, además de ejecutar composer install, para que mi aplicación web tenga todas las dependencias que necesita para poder ejecutarse correctamente.
  • logrotate.conf: si bien en logrotate.d tenemos la configuración específica para cada uno de los procesos, en este archivo se almacena la configuración general para todos los logs: cada cuánto se quieren rotar, el formato de los ficheros, etcétera.
  • nginx.conf al igual que el anterior, se trata de la configuración general del servidor Nginx donde estoy definiendo el número de conexiones, el formato de los logs, etcétera.
  • parameters.yml: como en esta aplicación estoy utilizando Azure Database for MySQL, he sacado este archivo fuera de symfony-demo/app/config por comodidad. En él simplemente especifico los valores necesarios para poder hacer la conexión con mi base de datos.
  • php.ini: configuración general de PHP.
  • sshd_config: se trata del archivo de configuración de openssh server. Si queremos acceder a nuestro contenedor a través del apartado SSH del App Service necesitamos tener un servidor SSH en nuestro contenedor.
  • supervisord.conf: para que supervisord sepa cuáles son los procesos que debe arrancar utilizamos este archivo donde le definimos el arranque del servidor ssh, php-fpm y nginx. En él he modificado el arranque de sshd para que se ejecute como proceso y no como servicio.
  • zz-docker.conf: configuración para php-fpm.

Creando la imagen de mi contenedor

Para crear mi imagen, basta con acceder a la raíz del proyecto y ejecutar el siguiente comando:

docker build . -t symfony-container

Este comando, como ya te expliqué cuando comencé con Docker, genera la imagen con la que podré crear mis contenedores, utilizando el archivo Dockerfile. Una vez que finalice el proceso podrás ver la misma en tu local.

Imagen symfony-container en local

¡No te olvides de cambiar los parámetros de conexión a tu MySQL!

Ejecutando el contenedor en local

Antes de desplegar tu nueva imagen en Web App for Containers te recomiendo que pruebes la misma en tu máquina local. Una vez que tienes la imagen generada, puedes lanzar este comando para crear un nuevo contenedor:

docker run -p 8000:80 -p 2222 symfony-container

Según esta configuración, podrás acceder a tu aplicación a través de http://localhost:8000 y si quisieras comprobar que el servidor SSH funciona correctamente deberías localizar cuál es el puerto por el que se está exponiendo el 2222.

Con docker ps podemos ver los puertos mapeados

Y ejecutar el siguiente comando para conectarte (la contraseña es Docker!):

ssh [email protected] -p 32768

Si todo funciona correctamente, ya puedes subir tu imagen al registro que elijas. Si por ejemplo quisieras subirlo a Docker Hub tendrías que etiquetar de manera correcta la misma:

docker tag symfony-container 0gis0/symfony-container

Y seguidamente hacer push a través de este comando:

docker push 0gis0/symfony-container

Para subirla a Azure Container Registry puede seguir estos pasos.

Desplegar tu imagen en Web App for containers

Ya tienes todo lo necesario para desplegar tu aplicación Symfony en Web App for containers. Accede al portal de Azure y en Create a resource busca por Web App for Containers. La configuración del asistente es tan sencilla como esto:

Configuración de Web App for Containers

Al cabo de unos instantes tendrás tu aplicación Symfony ejecutándose en un contendor en App Service. Podrás ver el proceso de descarga de la imagen y ejecución del container en el apartado Container settings.

El código lo tienes en mi GitHub.

¡Saludos!