intranetBatoi

Desplegament Docker de preproducció i producció

Este document completa la tasca de documentació de la issue #81 i descriu el flux recomanat per a construir, publicar i desplegar la imatge Docker de producció de la intranet. Els exemples estan inspirats en l’entorn de preproducció actual amb Caddy, però s’han simplificat perquè servisquen com a guia general.

Objectiu

La imatge de producció ha d’incloure el codi de l’aplicació i els assets compilats dins de la pròpia imatge. Això evita muntar el codi com a volum i fa el desplegament més previsible.

Els fitxers base del repositori són:

Què canvia respecte a desenvolupament

En desenvolupament, docker-compose.yml munta el repositori complet com a volum (.:/var/www/html). En producció o preproducció, docker-compose.prod.yml usa una imatge publicada i només munta els elements que han de persistir o injectar-se en runtime:

Build i push de la imatge

Des de l’arrel del projecte:

export IMAGE_TAG_PROD=laravel12-prod
docker build -f docker/8.3/Dockerfile.prod -t arturocandela/intranet:${IMAGE_TAG_PROD} .
docker push arturocandela/intranet:${IMAGE_TAG_PROD}

Si es vol un desplegament versionat, és preferible usar un tag explícit:

export IMAGE_TAG_PROD=2026.03.16
docker build -f docker/8.3/Dockerfile.prod -t arturocandela/intranet:${IMAGE_TAG_PROD} .
docker push arturocandela/intranet:${IMAGE_TAG_PROD}

La imatge resultant ja incorpora:

Preparar la màquina de preproducció o producció

Requisits mínims:

Exemple d’estructura en el servidor:

/opt/intranet/
  docker-compose.prod.yml
  Caddyfile
  .env
  storage/

La carpeta storage/ ha de persistir entre desplegaments perquè conté logs, fitxers pujats i altres artefactes de runtime.

Variables i fitxers sensibles

No s’ha de copiar mai el .env dins de la imatge. En este projecte, això es reforça de dues maneres:

Abans de publicar una imatge convé revisar:

docker run --rm --entrypoint /bin/sh arturocandela/intranet:${IMAGE_TAG_PROD} -lc 'ls -la /var/www/html | grep .env'
docker history --no-trunc arturocandela/intranet:${IMAGE_TAG_PROD}

El primer comandament hauria de mostrar com a màxim .env generat des de .env.example dins del procés de build, mai un .env real del servidor. El segon permet inspeccionar que no s’hagen introduït secrets en cap capa de la imatge.

Exemple orientatiu de docker-compose per a preproducció

L’arxiu del repositori ja inclou una base vàlida. Per a preproducció, l’important és mantindre este patró:

services:
  laravel.prod:
    image: arturocandela/intranet:${IMAGE_TAG_PROD:-laravel12-prod}
    restart: unless-stopped
    expose:
      - "80"
    volumes:
      - ./.env:/var/www/html/.env
      - ./storage:/var/www/html/storage

  caddy:
    image: caddy:2-alpine
    restart: unless-stopped
    ports:
      - "80:80"
      - "443:443"
    volumes:
      - ./Caddyfile:/etc/caddy/Caddyfile:ro
      - caddy_data:/data
      - caddy_config:/config

Notes:

Exemple orientatiu de Caddyfile

Per a una preproducció interna, el patró és tan senzill com:

preintranet.exemple.lan {
  reverse_proxy laravel.prod:80
  tls internal
}

Punts clau:

Arrancada i actualització

Una vegada copiats docker-compose.prod.yml, Caddyfile, .env i la carpeta storage al servidor:

export IMAGE_TAG_PROD=laravel12-prod
docker compose -f docker-compose.prod.yml pull
docker compose -f docker-compose.prod.yml up -d

Per a actualitzar a una nova versió:

export IMAGE_TAG_PROD=2026.03.16
docker compose -f docker-compose.prod.yml pull
docker compose -f docker-compose.prod.yml up -d

Verificacions posteriors al desplegament

Després d’alçar l’entorn, convé revisar:

Comandes útils:

docker compose -f docker-compose.prod.yml ps
docker compose -f docker-compose.prod.yml logs -f laravel.prod
docker compose -f docker-compose.prod.yml logs -f caddy

Observacions