La filosofía en Docker es utilizar un contenedor por servicio necesitado. Es decir que si vamos a implementar como es nuestro caso el día de hoy, una instancia de WordPress debemos tener un total de dos contenedores, uno para la base de datos ya sea de MySQL o MariaDB y otro para la aplicación WordPress que se ejecuta en este caso sobre un servicio Apache, completando de esta manera la idea de tener un contenedor por servicio.

Lo anterior no siempre se cumple, por ejemplo he observado que la imagen oficial Ampache (aunque no aparezca como oficial en Docker hub, sí aparece referenciada como oficial en el Github de Ampache) no sigue este principio. Si apreciamos el Dockerfile (tema de una entrada posterior) de la imagen se instala tanto el servicio de MySQL como de Apache y por consiguiente, todo los contenedores que se ejecuten con base en esta imagen tendrán dos servicios corriendo en su interior. A pesar de que lo anterior funcione de manera correcta, rompe con la regla general de uso de Docker, de tener un contenedor por servicio para así desacoplar los diferentes componentes (servicios) que va utilizar la aplicación.

Ejecutando WordPress uniendo dos contenedores

El día de hoy veremos cómo implementar con Docker de manera rápida y sencilla una instancia de WordPress mediante la utilización de las imágenes oficiales de WordPress y MySQL alojadas en Docker Hub. Primero que todo descargaremos las imágenes mediante docker pull:

$ docker pull wordpress
$ docker pull mysql

Las imágenes se pueden identificar por su nombre y adicionalmente de un tag que se indica con el formato imagen:tag y es este caso como no indicamos ningún tag Docker descarga las imágenes con el tag latest. Primero, vamos a ejecutar el contenedor de MySQL que servirá de base de datos para WordPress. Mediante la opción -e se pueden establecer variables de entorno para el contenedor:

$ docker run -d --name mysql00 -e MYSQL_ROOT_PASSWORD=admin mysql
  • -d Ejecuta el contenedor en background.
  • --name Establece el nombre del contenedor en mysql00.
  • -e MYSQL_ROOT_PASSWORD Contraseña del usuario root del servicio MySQL.
  • mysql Seleccionamos la imagen de MySQL previamente descargada como base para crear el contenedor.

Es el turno de crear el contenedor que tendrá la instancia de WordPress que usará como base de datos la instancia de MySQL creada en el paso anterior:

$ docker run -d --name wp00 --link=mysql00:mysql wordpress
  • --link Adicionamos el link del contenedor llamado mysql00 con el alias mysql (En este caso en concreto con WordPress, el contenedor se debe llamar o tener el alias mysql).

Es importante recalcar lo que sucede al unir los contenedores mediante la opción --link. Lo primero es que Docker en el contenedor de WordPress en su archivo hosts creará una entrada que apunta al contenedor de MySQL. El contenido del archivo hosts en el contenedor de WordPress lo podemos visualizar haciendo uso de docker exec:

$ docker exec wp00 cat /etc/hosts
127.0.0.1 localhost
::1 localhost ip6-localhost ip6-loopback
fe00::0 ip6-localnet
ff00::0 ip6-mcastprefix
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
172.17.0.2 mysql 26ed0c0fdf1d mysql00
172.17.0.3 6fd02e63d99b

Además de lo anterior, en el contenedor de WordPress se exportarán una serie de variables de entorno relacionadas con el servicio MySQL:

$ docker exec wp00 env | grep -i mysql
MYSQL_PORT=tcp://172.17.0.2:3306
MYSQL_PORT_3306_TCP=tcp://172.17.0.2:3306
MYSQL_PORT_3306_TCP_ADDR=172.17.0.2
MYSQL_PORT_3306_TCP_PORT=3306
MYSQL_PORT_3306_TCP_PROTO=tcp
MYSQL_NAME=/wp00/mysql
MYSQL_ENV_MYSQL_ROOT_PASSWORD=admin
MYSQL_ENV_GOSU_VERSION=1.7
MYSQL_ENV_MYSQL_MAJOR=5.7
MYSQL_ENV_MYSQL_VERSION=5.7.14-1debian8

Las variables de entorno que apreciamos, son usadas en el script docker-entrypoint.sh encargado entre otras cosas de validar la existencia de éstas y la generación del archivo de configuración de WordPress wp-config.php. Por lo anterior, no fue necesario indicar variables de entorno adicionales al momento de crear el contenedor de WordPress. A continuación, vemos un fragmento del script mencionado usando dichas variables:

docker-entrypoint.shdocker-entrypoint.sh
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
#!/bin/bash
set -e

if [[ "$1" == apache2* ]] || [ "$1" == php-fpm ]; then
  : "${WORDPRESS_DB_HOST:=mysql}"
  # if we're linked to MySQL and thus have credentials already, let's use them
  : ${WORDPRESS_DB_USER:=${MYSQL_ENV_MYSQL_USER:-root}}
  if [ "$WORDPRESS_DB_USER" = 'root' ]; then
    : ${WORDPRESS_DB_PASSWORD:=$MYSQL_ENV_MYSQL_ROOT_PASSWORD}
  fi
  : ${WORDPRESS_DB_PASSWORD:=$MYSQL_ENV_MYSQL_PASSWORD}
  : ${WORDPRESS_DB_NAME:=${MYSQL_ENV_MYSQL_DATABASE:-wordpress}}

  if [ -z "$WORDPRESS_DB_PASSWORD" ]; then
    echo >&2 'error: missing required WORDPRESS_DB_PASSWORD environment variable'
    echo >&2 '  Did you forget to -e WORDPRESS_DB_PASSWORD=... ?'
    echo >&2
    echo >&2 '  (Also of interest might be WORDPRESS_DB_USER and WORDPRESS_DB_NAME.)'
    exit 1
  fi
...

Las imágenes oficiales de MySQL (MYSQL_DATABASE, MYSQL_USER, MYSQL_PASSWORD, MYSQL_RANDOM_PASSWORD, etc) y WordPress (WORDPRESS_DB_HOST, WORDPRESS_DB_USER, WORDPRESS_DB_PASSWORD, WORDPRESS_DB_NAME, etc) aceptan diferentes variables de entorno por si queremos realizar una instalación más personalizada de cada uno de los servicios. Por ejemplo a las ya mencionadas variables de entorno en Wordpress, se puede indicar en el momento de creación del contenedor los secret keys que se deberían generar de manera aleatoria para cada instancia de WordPress mediante las siguiente variables de entorno:

WORDPRESS_AUTH_KEY
WORDPRESS_SECURE_AUTH_KEY
WORDPRESS_LOGGED_IN_KEY
WORDPRESS_NONCE_KEY
WORDPRESS_AUTH_SALT
WORDPRESS_SECURE_AUTH_SALT
WORDPRESS_LOGGED_IN_SALT
WORDPRESS_NONCE_SALT

Si todo ha salido bien ya deberíamos tener acceso al famoso instalador de WordPress, pero antes, debemos conocer la IP que Docker le asignó al contenedor de WordPress mediante docker inspect:

$ docker inspect wp00 | grep IPAddress
            "SecondaryIPAddresses": null,
            "IPAddress": "172.17.0.3",
                    "IPAddress": "172.17.0.3",
Instalación WordPress con Docker. Instalación WordPress con Docker.