Si, como yo, usas Linux en tus desarrollos, te habrás encontrado con que trabajar con las mismas versiones de software en tu sistema operativo que en producción puede llegar a ser un pequeño caos: dependencias que no puedes cumplir, no dispones de paquetería específica y acabas teniendo que compilar a mano servicios que, en muchas ocasiones, implican horas de cambios y reintentos para conseguir que todo funcione medianamente bien.
Por suerte, con la llegada de los contenedores y de Docker, muchos de estos problemas pertenecen ya al pasado. Para que veas lo sencillo que puede ser, preparamos un entorno con Apache, PHP y MySQL que puedes utilizar para probar tu web.
Índice de contenidos
¿Qué es Docker?
Docker es un servicio que permite ejecutar pequeños contenedores de software sobre el núcleo de nuestro sistema operativo, por lo que es una opción más rápida y liviana que el uso de máquinas virtuales.
Por regla general, se suele empaquetar un solo servicio por contenedor, por lo que, para nuestro ejemplo, vamos a necesitar un orquestador, es decir, una herramienta que nos permita manejar en conjunto varios contenedores relacionados entre sí. De ahí el uso de Docker Compose.
Para servicios conocidos (Apache, PHP, MySQL, MongoDB…), tenemos contenedores oficiales disponibles en Docker Hub. Puedes distinguir fácilmente estas imágenes, puesto que están marcadas como official.
¡A jugar!
Hasta aquí la parte «aburrida». Toca probar el juguete nuevo 😀
Vaya… No lo tengo instalado
Como ya habrás deducido, lo primero que necesitas es tener instalados Docker y Docker Compose en tu máquina. En muchas distribuciones Linux ya está incluido como parte de la paquetería disponible, por lo que podrás instalarlo desde tu herramienta de gestión de paquetería preferida. Pero, si prefieres estar a la última o no tienes disponible el paquete, siempre puedes seguir las instrucciones de la documentación:
Si usas Linux, mi consejo es que, a mayores, sigas los pasos de instalación adicionales. Te ayudarán, por ejemplo, a no depender de ser root, o de utilizar sudo, incluyendo a tu usuario en el grupo de Docker.
Ahora que ya tengo Docker, ¿cómo lo configuro?
Para poder levantar los servicios que necesitas, tienes que indicarle a Docker Compose de alguna forma lo siguiente:
- Contenedores a crear/levantar
- Relación de los contenedores entre sí
Para ello creamos un fichero YAML, llamado «docker-compose.yml», donde definimos cada uno de los servicios (puedes ver el fichero completo al final de esta sección).
Comienza tu fichero de configuración indicando la versión de sintaxis a utilizar y abriendo la sección de servicios:
version: "3" services:
Configuración para MySQL
Primero, nos fijamos en el servicio donde incluiremos nuestra base de datos con el contenedor oficial de MySQL, que permite definir incluso el nombre de la base de datos que queremos usar, junto a sus datos de acceso. Actualmente, la última versión estable de MySQL es la 5.7, por lo que las líneas a incluir en el fichero son:
miservicio_mysql: image: mysql:5.7 environment: - MYSQL_DATABASE=nombre - MYSQL_ROOT_PASSWORD=claveroot - MYSQL_USER=miusuario - MYSQL_PASSWORD=mipassword volumes: # Montamos un volumen para MySQL para no perder los datos de bd - ./volumenes/mysql:/var/lib/mysql expose: - 3306
Una pequeña mejora. Si quieres acceder fácilmente al servicio MySQL desde tu aplicación favorita, puedes hacer que escuche en el puerto 3306 local, o en el que tú prefieras, solamente con añadir:
ports: - 3306:3306
Configuración para el servidor web
Aquí, por ser la opción más sencilla, usamos el contenedor oficial de PHP con Apache ya integrado, aunque también podríamos combinar un contenedor oficial de Apache con la versión FPM de este contenedor de PHP.
Como puedes ver en la documentación del contenedor, puedes elegir entre varias versiones:
- php: 7-Apache. Última versión de PHP 7, actualmente la 7.2
- php: 7.2-Apache. Última versión estable de PHP 7.2
- php: 7.1-Apache. Última versión estable de PHP 7.1
- php: 7.0-Apache. Última versión estable de PHP 7.0
- php: 5.6-Apache. Última versión estable de PHP 5.6
Para este ejemplo me he decantado por usar la versión más actual de PHP 7. El servicio se configura así:
miservicio_php: image: php:7-apache volumes: # Montamos nuestra web desde fuera en el directorio web del contenedor - ./miweb/:/var/www/html expose: - 80 ports: - 80:80 links: - miservicio_mysql
Con esto queda listo el fichero de configuración, así que ya podrías levantar el fichero. Por si prefieres copiar y pegar, aquí tienes la configuración completa de este ejemplo:
version: "3" services: miservicio_mysql: image: mysql:5.7 environment: - MYSQL_DATABASE=nombre - MYSQL_ROOT_PASSWORD=claveroot - MYSQL_USER=miusuario - MYSQL_PASSWORD=mipassword volumes: # Montamos un volumen para MySQL para no perder los datos de bd - ./volumenes/mysql:/var/lib/mysql expose: - 3306 ports: - 3306:3306 miservicio_php: image: php:7-apache volumes: # Montamos nuestra web desde fuera en el directorio web del contenedor - ./miweb/:/var/www/html expose: - 80 ports: - 80:80 links: - miservicio_mysql
Añadiendo tu código y levantando Docker
Ya solo falta que incluyas el código en el directorio «miweb», o el que hayas indicado en tu configuración, y ya podrás iniciar todos los servicios.
¡Un detalle! Asegúrate de que no tienes nada en tu máquina que esté utilizando los puertos que hemos definido para nuestros servicios (80 y 3306), pues de lo contrario no podrás iniciar los contenedores.
Lanzando contenedores en background
Esta es la opción más cómoda a la hora de no cerrar todo accidentalmente ya que, al quedar lanzados los contenedores en segundo plano, seguirán funcionando aunque cerremos la terminal. A cambio, para ver los logs tendrás que usar comandos de Docker para cada contenedor por separado. Para iniciar así el contenedor, solamente tendrás que situarte en la misma carpeta donde está el fichero docker-compose.yml y ejecutar:
docker-compose up -d
Si quieres detener los contenedores, puedes hacerlo también con el comando:
docker-compose down
Lanzando contenedores en primer plano
Si, por el contrario, prefieres ver los logs directamente en pantalla y poder parar los contenedores solamente con pulsar Ctrl+C, inicia el servicio en primer plano, ejecutando el de inicio, pero sin «-d»:
docker-compose up
¡Y listo! Ya tienes funcionando un servicio web, con PHP 7.2 y MySQL 5.7, con el código de tu web en tu máquina. Solamente tendrás que acceder a http://localhost/.
Recuerda que este es un tutorial muy sencillo, con lo básico para arrancar los servicios y que funcionen, pero los límites los pones tú:
- Añade extensiones al php y Apache, creando tu propio contenedor
- Cambia rutas, configuraciones, variables de entorno…
- Juega con el mapeo de puertos, por ejemplo:
- Añade un segundo servidor web, con otro php y escuchando en otro puerto (por ejemplo 81, 8080), para probar tu web con diferentes versiones
- Cambia el puerto del apache para mantener levantado tu servicio local
- …
¡Esperamos tus comentarios! Si te ha resultado útil, si quieres que profundicemos más en el tema… Recuerda que también puedes contactarnos si tienes cualquier duda o sugerencia, ¡que para eso estamos! 😀
50 comentarios
Que terminal es la que usas ? cmder???
Gracias!
muy buen post!
Hola!
Me alegra que el post te haya gustado y espero que te resulte útil.
Sobre la terminal, utilizo la que viene por defecto en Ubuntu, pero he añadido bash-git-prompt para que me muestre datos sobre el repositorio de código, con algún cambio en los temas que trae por defecto. Usando asciinema he capturado todo lo que pasaba por la terminal y generado un gif para el post.
Un saludo! 😉
como harias para añadir phpmyadmin porque tengo un problema con ello y no consigo que enlace con la base de datos
Hola Diego!
La forma más sencilla es incluir el contenedor oficial de phpMyAdmin como un componente más, escuchando en el puerto 8080 de tu máquina y enlazado al contenedor de MySQL para que pueda acceder la base de datos. De esta forma podrás acceder al phpMyAdmin con la url http://localhost:8080/.
Te dejo un ejemplo en este fragmento de código.
Espero que esto te sirva de ayuda y no dudes en contactar de nuevo con nosotros si lo necesitas 😉
phpmyadmin:
image: phpmyadmin/phpmyadmin:latest
container_name: seafile-phpmyadmin
restart: always
links:
– miservicio_mysql
ports:
– «8181:80»
environment:
– MYSQL_USERNAME=miusuario
– MYSQL_ROOT_PASSWORD=mipassword
Hola Víctor!
Muy bueno post! estuve intentando levantar el servidor pero me esta dando problemas con los permisos en el volumen «miweb» me podrías dar algún consejo de que podría hacer ??
Hola gallbers!
Me alegra que te guste la entrada 🙂 Sobre tu consulta:
Si utilizas Linux, no debería ser necesario configurar nada para montar directorios de tu máquina en los contenedores, solamente debes recordar lanzar los comandos como root (vale con sudo) o añadir tu usuario al grupo «docker» para no necesitarlo.
En el caso de Windows 10, con Docker for Windows, es posible que tengas que habilitar el uso de las unidades de disco de tu PC dentro de la configuración del propio Docker. Te dejo una captura:
En algunos casos, en Docker for Windows, si la unidad ya estaba compartida, la solución suele ser eliminarla de compartidos y volverla a compartir.
De todas formas, si esto no te soluciona el problema, o utilizas otro sistema operativo, no dudes en contactar de nuevo y estaremos encantados de ayudarte.
Un saludo!
Hola Víctor me gusto muchoo este post gracias.
Sabrías como poner una IP al contenedor para que no tenga que escribir «localhost», si no una IP propia del contenedor?
Hola Yolanda!
Muchas gracias por tu comentario, siempre es agradable saber que a la gente le gusta lo que publicamos 😉
Sobre tu pregunta, tienes varias opciones a la hora de acceder por IP:
– Usar la IP de la máquina (PC, servidor…) en la que estás levantando el servicio
– Obtener, mediante comandos de Docker, la IP que Docker ha asignado al contenedor
– Definir una red la configuración de Docker Compose y asignar direcciones de esta red a los contenedores
Te explico las dos últimas con un poco más de detalle:
Usar la IP asignada por Docker al contenedor
De las dos opciones que voy a explicar esta es la más sencilla, aunque tiene el inconveniente de que la dirección IP puede cambiar al detener y volver a levantar los contenedores.
El comando docker inspect nos da todos los detalles sobre un contenedor, pero podemos limitar su respuesta especificando un formato para la misma, así haremos nos devuelva solamente el dato que nos interesa (por ejemplo, la dirección IP).
En mi caso, mi contenedor se llama «apachephpdocker_miservicio_php_1» (para obtener un listado de los contenedores activos ejecutamos el comando «docker ps«), por lo que ejecuto el comando:
docker inspect apachephpdocker_miservicio_php_1 –format='{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}’
Con esto me devuelve el valor de la IP del contenedor:

Usando esta IP en nuestro navegador, siempre que Docker y el navegador estén en la misma máquina, podemos acceder al servicio.
Definir la red de Docker para nuestros contenedores con Docker Compose
Esta es una opción más avanzada que la anterior, las direcciones IP se mantienen, pero tenemos que tener cuidado con las redes que definimos para no tener conflictos con las direcciones.
En este caso, definimos una nueva sección del fichero docker-compos.ymle para las redes, al mismo nivel que la de servicios y la usamos para asignar IPs a los contenedores.
Para no alargar más el contenido del comentario, he actualizado este fragmento de código, de mi anterior comentario, para incluir también un ejemplo con configuraciones de red.
Si tienes cualquier otra consulta, no dudes en contactar de nuevo, estaremos encantados de ayudarte.
Un saludo!
Hola,
A mi el apache me deja esto en el log y no logro ver «localhost:8090» (le cambie el puerto)
AH00558: apache2: Could not reliably determine the server’s fully qualified domain name, using 172.23.0.3. Set the ‘ServerName’ directive globally to suppress this message
[Thu Feb 20 01:29:31.208942 2020] [mpm_prefork:notice] [pid 1] AH00163: Apache/2.4.38 (Debian) PHP/7.4.2 configured — resuming normal operations
[Thu Feb 20 01:29:31.208985 2020] [core:notice] [pid 1] AH00094: Command line: ‘apache2 -D FOREGROUND’
[Thu Feb 20 01:50:16.579510 2020] [mpm_prefork:notice] [pid 1] AH00169: caught SIGTERM, shutting down
[Thu Feb 20 13:46:19.189547 2020] [mpm_prefork:notice] [pid 1] AH00163: Apache/2.4.38 (Debian) PHP/7.4.2 configured — resuming normal operations
[Thu Feb 20 13:46:19.189707 2020] [core:notice] [pid 1] AH00094: Command line: ‘apache2 -D FOREGROUND’
HEEEELPPP
Hola Jonathan,
En principio no deberías tener problemas para cambiar el puerto y que funcionase en el 8090, yo lo he probado con la siguiente configuración:
version: "3"
services:
miservicio_mysql:
image: mysql:8
environment:
- MYSQL_DATABASE=nombre
- MYSQL_ROOT_PASSWORD=claveroot
- MYSQL_USER=miusuario
- MYSQL_PASSWORD=mipassword
volumes:
- ./volumenes/mysql:/var/lib/mysql
expose:
- 3306
ports:
- 3306:3306
miservicio_php:
image: php:7-apache
volumes:
- ./miweb/:/var/www/html
expose:
- 80
ports:
- 8090:80
links:
- miservicio_mysql
En los logs puedes ver que el apache responde correctamente:
AH00558: apache2: Could not reliably determine the server's fully qualified domain name, using 172.19.0.3. Set the 'ServerName' directive globally to suppress this message
AH00558: apache2: Could not reliably determine the server's fully qualified domain name, using 172.19.0.3. Set the 'ServerName' directive globally to suppress this message
[Mon Feb 24 08:01:12.335705 2020] [mpm_prefork:notice] [pid 1] AH00163: Apache/2.4.38 (Debian) PHP/7.4.3 configured -- resuming normal operations
Mon Feb 24 08:01:12.335753 2020] [core:notice] [pid 1] AH00094: Command line: 'apache2 -D FOREGROUND'
172.19.0.1 - - [24/Feb/2020:08:01:14 +0000] "GET / HTTP/1.1" 200 22300 "-" "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:72.0) Gecko/20100101 Firefox/72.0"
Revisa que tu configuración sea correcta y recuerda que, si no tienes nada en el directorio con el código de la web (./miweb/), el apache te devolverá un error 403 (Forbidden).
Espero haberte sido de ayuda. si necesitas cualquier otra cosa, no dudes en volver a contactar o comentar.
Un saludo 😉
Revisa que tu configuración sea correcta y recuerda que, si no tienes nada en el directorio con el código de la web (./miweb/), el apache te devolverá un error 403 (Forbidden).
Como hago esta configuración que tu dices?
buen aporte.
Saludos!!!
Hola JB,
Principalmente asegúrate de que los puertos están definidos en el orden correcto en el docker-compose.yml, siempre primero el puerto de la máquina «anfitrión» y luego el puerto del contenedor. También de que la carpeta que montas es la correcta (a mí ya me ha jugado alguna mala pasada omitir un punto y usar «/carpeta» en lugar de «./carpeta»…).
Por lo demás, con el resto de configuraciones no deberías tener problemas.
Espero haberte sido de ayuda. Un saludo 😉
Hola.
Muy bueno el post!
Consultas:
1.- pude levantar ambos dockers sin problema, pero como sólo tengo carpetas dentro del directorio me devuelve «Forbidden» como explicaste. El problema es que dentro de las carpetas sí tengo archivos index.php y no me los reconoce.
Podrías indicarme que hacer? Es un tema de configuración del docker con apache o es problema de mi SO host?
2.- Para hacer lo mismo para sistemas con Windows, tengo que compartir una carpeta dentro del directorio del usuario o puedo compartir cualquier carpeta con el docker?
version: ‘3.0’
services:
apache:
image: php:7.4-apache
container_name: apache
expose:
– 80
ports:
– 80:80
volumes:
– /var/www/html:/var/www/html
links:
– mysql:mysql
mysql:
image: mysql:8.0.13
container_name: mysql
expose:
– 3306
ports:
– 3306:3306
command: –default-authentication-plugin=mysql_native_password
environment:
MYSQL_DATABASE: db
MYSQL_ROOT_PASSWORD: root
volumes:
– /var/lib/mysql:/var/lib/mysql
Esto es desde un sistema con SO Ubuntu 18.04.
Desde ya, muchas gracias!
Hola Juan,
Sobre el contenido en carpetas, aunque al acceder a «http://localhost/» te muestre el «forbidden», debería de funcionar correctamente si añades manualmente la carpeta a la URL (por ejemplo: «http://localhost/micarpeta»). De todas formas, siempre puedes cambiar el comportamiento de Apache creando tu propio fichero «000-default.conf» y montándolo como volumen en el contenedor. Mi consejo si haces esto: crea una carpeta, dentro de esta pon el fichero «000-default.conf» y móntala como un volumen en la ruta /etc/apache2/sites-available/ del contenedor de PHP. Recuerda que si la configuración de Apache no es correcta, el contenedor finalizará (por el error de Apache).
Con Windows, si tienes habilitado el acceso de Docker a la unidad (lo tienes en un comentario anterior de esta entrada) y puedes acceder a la carpeta, no deberías de tener problemas en usarlas en Docker, al menos lo poco que yo lo he probado en este sistema operativo.
Espero haber resuelto tus dudas.
Un saludo 😉
No entiendo porque expones el puerto y luego lo declaras? cual es el fin de esto?
Hola Daniel,
En este caso, «expose» y «ports» hacen 2 cosas distintas:
Los puertos definidos en expose solamente se exponen a los servicios en la red interna que se crea entre ellos, pero no estarían accesibles en la máquina que ejerce de anfitrión.
Los puertos definidos en ports se mapean a puertos de la máquina anfitrión haciendo más sencillo acceder a los servicios.
Realmente, de acuerdo con la documentación de Docker Compose, solo necesitaríamos exponer del puerto 3306 de MySQL en la red interna del Docker y mapear los puertos del servicio web a nuestra máquina.
Espero haber resuelto tu consulta.
Un saludo 😉
Muy bueno el post, me podrías indicar cómo hacer que mi proyecto de docker compose levante automáticamente cuando se reinicia el server , que no lo tenga que hacer manualmente.
Hola Adrian,
Docker Compose tiene ya una opción específica para reiniciar los servicios automáticamente, solo tendrías que añadir la opción «restart: always» a cada uno de los servicios del docker-compose.yml que quieres que siempre estén activos. Por ejemplo:
Espero haber solucionado tu duda.
Un saludo 😉
Realmente muy bueno el post.
Tengo un pequeño problema. Por supuesto, en local funciona ala perfeccion. Cuando lo subo a mi VPS, no hay forma de abrir el PHPmyadmin. Con la URL:8080 no encuentra el servicio.
¿Como puedo solucionarlo?
Muchisimas gracias por adelantado.
Hola Sergi,
En este caso podría deberse a varias cosas:
En primer lugar comprueba que todos los contenedores están levantados, puedes hacerlo con el comando «docker-compose ps» y fíjate que todos están en estado «Up». Si el de phpMyAdmin no lo estuviera, prueba a levantar todo sin el «-d» para ver los logs y ver lo que pasa, es posible que el puerto 8080 ya esté en uso por alguna otra aplicación o servicio.
Si todo está correcto, revisa las posibles reglas de firewall en la máquina, seguramente tengas limitado/bloqueado el acceso a puerto 8080 de la misma. En este caso podrás optar por habilitar el acceso al puerto en el firewall de tu máquina o utilizar otro puerto que no tengas bloqueado.
Recuerda que si tienes cualquier duda con tu servidor, siempre puedes ponerte en contacto con nuestro Equipo de Soporte y te ayudarán a resolverlo sin problemas.
Espero haber resuelto tus dudas.
Un saludo 😉
Hola Victor! Muy buen post!
Si tenemos tres contenedores, uno corriendo Apache, otro PHP con el código fuente y otro corriendo MySql ¿Cada uno de ellos son Microservicios o simplemente servicios?
Hola Ramiro,
La verdad es que, cuando pienso en un microservicio, me imagino algo más complejo que un MySQL por si mismo, o un Apache2. Entiendo que un microservicio es funcional por si solo, aunque el resto de microservicios con los que interactúa no estén activos en este momento.
Sin embargo, podríamos preguntarle a varios desarrolladores y acabaríamos generando un debate sobre esto, en el que parte los verían como microservicios y otros no. Al final es un tema de como lo percibimos cada uno de nosotros.
¡Un saludo!
Si ya tengo laradock en docker, es decir, levante un proyecto de laravel con laradock usando nginx, mysql, phpmyadmin, mi pregunta es, ¿Si quiero un proyecto que requiere esos contenedores, debo configurarlo aparte, seguir este tutorial, o me sirven los contenedores que ya tengo?
Es confusa mi pregunta ¿?, espero que no.
Gracias de antemano.
Hola Yulianny,
No conocía Laradock, pero le he echado un vistazo rápido y, por lo que he podido ver, ya te da un entorno de desarrollo mucho más completo que el que conseguirías tener siguiendo este tutorial al pie de la letra.
Según veo en sus características, puedes gestionar varios proyectos con un solo Laradock o tener múltiples Laradocks, uno por proyecto.
Si vas a trabajar con Laravel yo le daría una oportunidad, tiene muy buena pinta.
Espero haber resuelto tu pregunta 😉
¡Un saludo!
Sí, está genial, ya lo estoy probando, sí me sirvio sus comentarios, para aclarar dudas.
MI inquitud era especificamente con los contenedores, que si debía crearlos otra vez, y eso hice, uno parecido al que tiene acá pero con phpmyadmin, y me va bien. Lo dejaré por si alguien más lo desea usar.
version: ‘2’
services:
mysql:
image: mysql:8.0
container_name: mysqlserver
command: –default-authentication-plugin=mysql_native_password
working_dir: /application
volumes:
– .:/application
restart: always
environment:
– MYSQL_ROOT_PASSWORD=123456
– MYSQL_DATABASE=BD
– MYSQL_USER=root
– MYSQL_PASSWORD=123456
ports:
– «8082:3306»
website:
container_name: php73
build:
context: ./
links:
– «mysql:database»
volumes:
– ./src:/var/www/html
ports:
– 8000:80
depends_on:
– mysql
phpmyadmin:
image: phpmyadmin/phpmyadmin
container_name: phpmyadmin
environment:
– PMA_ARBITRARY=1
restart: always
ports:
– 8080:80
volumes:
– /sessions
Y en caso de que me sirva, me recomiendas algún tutorial o post que me ayude con eso, por fa.
Hola de nuevo,
Como te indicaba en mi otro comentario, no conocía Laradock, aunque, ahora que lo he visto, me parece interesante.
Ante este desconocimiento, no sabría recomendarte un tutorial específico. Yo empezaría por el «Getting Started» de su documentación y luego buscaría en mi buscador preferido.
Espero haberte sido de ayuda.
¡Un saludo! 😉
Funciona, genial. Dockers es otro mundo.
Cómo ponerle una IP del mismo rango que el host?
Un saludo y ánimos!
Hola César,
La verdad es que esto es algo que nunca me había planteado, hasta ahora solamente «mapeaba» los puertos que necesitaba al host para poder acceder a ellos.
Lo he estado revisando y no he conseguido hacer funcionar algo correctamente asignado direcciones en esa misma red que el host.
De todas formas, si en un futuro consigo hacerlo funcionar, ten por seguro que te responderé de nuevo a este comentario (o, si es lo bastante grande, se convertirá en una nueva entrada en el blog).
Gracias por comentar! Un saludo 😉
Hola, me parecio excelente tu post, ahora necesito una mano, necesito que esta activo pdo-mysql y mysqli
Hola Seienshi,
En este caso tendrás que personalizar el contendor web creando tu propio «Dockerfile», siguiendo las instrucciones que se indican en la documentación del propio contenedor de PHP.
Lo más sencillo es que partas del contenedor que usamos (php con apache) y en tu Dockerfile personalizado hagas que instale las extensiones que te interesa con la instrucción «docker-php-ext-install», haciendo algo similar a esto:
FROM php:7-apache
RUN docker-php-ext-install pdo pdo_mysql mysqli
Luego solo tendrás que cambiar tu «docker-compose.yml» para que, en lugar de usar una imagen por defecto, construya la que acabas de definir, cambiando el «image: php:7-apache» por un «build: ruta/carpeta/deldockerfile» o «build: .» si el dockerfile está en la raíz.
Espero haber resuelto tu consulta.
Gracias por comentar. Un saludo 😉
Buenas muy bueno el post, mi consulta o mas bien una orientación. Tengo un aplicación básica( ya terminada) que quiero que se utilice en un entorno local, la cual esta desarrollada en Angular y consume una api de Laravel y un motor postgre.
Ahora es posible deployar y correr de forma local sin llevarlo a un servidor web utilizando docker?? o existe alguna otra herramienta con la cual pueda investigar para este cometido?
Desde ya muchas gracias
Hola Alejandro,
No deberías tener problema, siempre que en la máquina donde quieres hacerlo funcionar tengas disponibles Docker y Docker Compose, o puedas instalarlos.
Puedes partir de una configuración similar a la de este post, cambiando el contenedor de MySQL por el de PostgreSQL e irla adaptando a tus necesidades. Posiblemente necesites personalizar el contenedor de PHP (hay un comentario anterior donde se da una explicación de como habilitar pdo_mysql que te puede servir) o, incluso, te puedes plantear el uso de Laradock.
Otra opción es la de crear tu propio contenedor de PHP partiendo de una imagen básica del sistema operativo, como podrían ser Ubuntu o Debian. En este caso, ten en cuenta que tendrás que preparar todo tú (servidor web, php, librerías…) y dedicar mucho más tiempo, pero tendrás el contenedor tal y como quieres que sea.
Espero haber resulto tu consulta.
Gracias por comentar. Un saludo 😉
Lo estoy invetigandooo!Gracias por tu respuesta, te lo agradezco.
Muchas gracias por el tutorial! Muy completo! Soy totalmente novata en Docker y también bastante en php.
Estoy desarrollando una aplicación php en Docker. He utilizado el código ampliado que indicaste con un tercer contenedor phpmyadmin.
Quiero acceder a phpmyadmin (con localhost:8080 que es el puerto asingado) a través del navegador pero me aparece el siguiente error:
phpMyadmin – Error
Error during session stat_ please check your PHP and/or webserver log file and configure php installation properly. Also ensure that are enabled in your browser.
session_write_close() write failed. No space left on device (28)
session_write_close():Failed to write session data (files). Please verify that the current of session_save_path is correct ().
He comprobado que sí que tengo espacio en /var tanto de la máquina host como del contenedor. No sé por qué puede ser, si es que tengo que configurar algún archivo más para dar acceso remoto…
Agradecería alguna idea please!!!
Gracias!
Saludos!
Hola Luias,
¡Gracias por comentar!
Sin los logs de error no podríamos saber con mayor exactitud qué sucede. De todas formas, lo mejor sería:
1. Vaciar la caché del navegador y eliminar las Cookies
2. Verificar que /var/lib/php/session/ tenga permisos de acceso
3. Verificar en el php.ini que la directiva session.save_path esté correctamente establecida
Un saludo!
Ante todo muchisimas gracias por la aclaratoria anterior.
Ahora tengo otra duca, tengo en un vps dos contenedores cada uno con un sitio web distinto, un sitio lo publico por el puerto 80 del anfitrion y el otro por el 8080, hasta alli todo bien, pero ahora debo hacer que sean visibles al mundo, tengo solo una ip, pero el sitio que publico por el puerto 80 debe apuntar a dominioa.com y el que publico por el puerto 8080 debe apuntar a dominiob.com
Creo que lo que necesitas es un Reverse-proxy. Basicamente es un servidor que recibe pedidos externos y los reenvia a los servicios internos que correspondan.
Fijate en Traefik que tambien viene en contenedor
¡Hola!
Asumiendo que están los puertos 80 y 8080 del Docker mapeados con el 80 y 8080 del VPS, y que está correcta la configuración del servicio web y sus VirtualHost (Apache) o ServerBlock (Nginx), entonces habría que apuntar la zona @ de cada uno de los dominios a la IP del VPS. Con esto, luego de que se propague la zona, el dominio será accesible a nivel público.
¡Esperamos haberte sido de ayuda!
Hola felicitaciones por el excelente blog!
Por favor podrías orientarme respecto de lo siguiente, estoy experimentando con docker-compose y joomla.
Utilicé el procdimiento que plantea bitnami y todo funciona muy bien.
Pero ahora tengo la necesidad de instalar un certificado SSL, y encontré un tutorial para que mediante jrcs/letsencrypt-nginx-proxy-companion pueda agregarlo, sin embargo mi pregunta es, ¿si detengo el actual contenedor con docker-compose down y luego modifico el docker-compose.yml para finalmente levantarlo nuevamente con docker-compose up -d, el sitio que existía no se verá dañado?
¡Hola!
Cuando se monta el volumen en el docker-compose.yml, lo que hace es enlazar la carpeta indicada del anfitrión con la indicada del Docker. Por ejemplo:
volumes:
– ./miweb/:/var/www/html # Donde miweb es la carpeta del anfitrión y /var/www/html la del docker.
Si se hacen cambios tanto desde fuera del Docker (en la carpeta miweb) como desde dentro del Docker (/var/www/html), estos cambios serán permanentes, por lo que en el momento de hacer un docker-compose down no se eliminará contenido.
¡Esperamos haberte sido de ayuda!
Muy buen post! Bien Claro y simple, gracias!!!
A ti por comentar, Mauricio. Quedamos a tu disposición para lo que necesites.
Hola agradezco mucho la ayuda con esto, solo que aunque ya se crearon mis contenedores, cuando lanzo en localhost me aparece un Forbiden, ya lei los demas comentarios y aconsejas desde windows compartir el recurso de la carpeta donde esta mi proyecto que quiero correr con docker pero aun y con eso no me permite verlo
¿alguna recomendacion? Gracias de antemano
Hola Julio,
Aunque un Forbidden podría darse por muchos motivos, tal y como hemos montado este escenario te recomendaríamos lo siguiente:
-Verifica que tienes permisos en la carpeta donde tienes la web.
-Verifica que la carpeta tiene contenido. Si intentas acceder a la web y no tienes ningún fichero este también podría ser el motivo del error. Podrías crear un fichero index.html o index.php (con sintaxis correcta) en caso de no tenerlo y acceder de nuevo.
¡Un saludo!
Hola, me encanto el post, para personas como yo que estan iniciando en este mundo de docker es de mucha ayuda post como estos.
Ahora mi consulta es, resulta que necesito instalar en un contenedor docker aparte un CMS (sea Worpress o Drupal), enlazarlo con apache y php, y a mi base de datos aparte (es lo que piden en el proyecto) ¿Como puedo hacer esto? resulta que Nginx es sumamente fácil pero no he encontrado un solo post que lo haga con apache en docker. ¿Me podrian ayudar con eso?
Hola Adrian,
Entiendo que lo que necesitas es que WordPress o Drupal funcionen con Apache y PHP, quizás la opción más sencilla sea usar los contenedores oficiales de WordPress o Drupal que tienes disponibles en Dockerhub, ambos usan por defecto Apache.
En ambos casos tienes ejemplos en la propia documentación en dockerhub de como lanzar ambos servicios junto a otro contenedor a parte con la base de datos mediante docker hub, con MySQL para WordPress y con PostgreSQL para Drupal.
Espero haber resuelto tus dudas.
Gracias por comentar. Un saludo 🙂
Gracias por el post!!! tengo el siguiente docker-compose :
version: «3.0»
networks:
laravel:
services:
nginx:
image: nginx:1.18.0-alpine
container_name: nginx
ports:
– «8088:80»
volumes:
– ./backend:/var/www/html
– ./nginx/default.conf:/etc/nginx/conf.d/default.conf
depends_on:
– php
– mysql
networks:
– laravel
mysql:
image: mysql:5.7.31
container_name: mysql
restart: unless-stopped
tty: true
ports:
– «4306:3306»
volumes:
– ./mysql:/var/lib/mysql
environment:
MYSQL_DATABASE: cec
MYSQL_USER: admin
MYSQL_PASSWORD: admin
MYSQL_ROOT_PASSWORD: admin
SERVICE_NAME: mysql
SERVICE_TAGS: dev
networks:
– laravel
php:
build:
context: .
dockerfile: Dockerfile.backend
container_name: php
volumes:
– ./backend:/var/www/html
ports:
– «9000:9000»
networks:
– laravel
composer:
image: composer:1.8.6 #especificar tags
container_name: composer
volumes:
– ./backend:/var/www/html
working_dir: /var/www/html
networks:
– laravel
npm:
build:
context: .
dockerfile: Dockerfile.frontend
container_name: npm
ports:
– «4200:4200»
volumes:
– ./frontend:/app
# working_dir: /app
# entrypoint: [«npm»]
networks:
– laravel
artisan:
build:
context: .
dockerfile: Dockerfile.backend
container_name: artisan
volumes:
– ./backend:/var/www/html
depends_on:
– mysql
working_dir: /var/www/html
entrypoint: [«php», «/var/www/html/artisan»]
networks:
– laravel
tengo una problema con docker-compose y no logro solucionarlo, el tema es cuando construyo las contenedores tengo problema de permiso de modificación e incluso ejecute:
chmod -R gu+w
chmod -R guo+w
en el contenedor y me permite la modificación pero si agrego otro archivo ese no me deja.
Alguna sugerencia? se lo agradecería.
Saludos
Hola Alejandro,
Piensa en cada uno de tus contenedores como si fuera una máquina distinta en la que, cuando creas un usuario o un grupo, a estos se les asigna un identificador (UID para usuarios, GID para el grupo).
Si compartes volúmenes/carpetas entre diferentes máquinas y el UID o el GID no coinciden, este usuario no dispondrá de los permisos adecuados.
Un ejemplo: el contenedor oficial de Apache con PHP ejecuta el Apache con el usuario www-data y el UID 33. Cualquier fichero o carpeta que crees desde una aplicación PHP de ese contenedor tendrá los permisos definidos para el usuario con UID 33 que funcione en otro contenedor diferente y que acceda al mismo volumen.
Si los contenedores son tuyos propios y creas usuarios, puedes intentar crearlos asegurándote de que tienen el mismo UID, de forma que sepas que van a poder compartir los ficheros. Si partes desde otros contenedores siempre puedes «extenderlos», usándolos como base de tu Dockerfile e incluyendo los cambios que necesites.
¡Espero haberte ayudado!
Gracias por comentar 😉