TrafficServerLocal/docs/arquitectura.md
merios 33c368936e feat: infraestructura base de Traefik + generador de proyectos
- core/: reverse proxy Traefik v3 (HTTP 80 / HTTPS 443)
  - traefik.yml con provider Docker (exposedByDefault: false) y provider file
  - dynamic_tls.yml sanitizado con certificados .local comentados
  - certs/README.md con procedimiento de certificados auto-firmados
- init_project.sh: generador de proyectos base (SRV_DIR configurable)
  - plantilla compose con redireccion HTTP->HTTPS + Let's Encrypt
  - bloque alternativo comentado para dominios .local
- README.md: documentacion integral (puesta en marcha, HTTP/HTTPS,
  troubleshooting y seguridad)
- docs/arquitectura.md: guia de instalacion y gestion de URLs
- docs/http-https.md: referencia de etiquetas Traefik, TLS y certresolver
- .gitignore: excluye .env, acme.json, certificados, datos y respaldos
2026-10-15 11:34:39 -03:00

246 lines
5.8 KiB
Markdown

# Arquitectura del servidor y gestión de URLs
Guía de instalación del entorno base en el host (`~/srv`), despliegue de la
infraestructura común y alta de proyectos Docker enlazados al proxy inverso.
> Documento de referencia. Para el detalle fino de etiquetas TLS ver
> [`http-https.md`](http-https.md).
---
## 1. Configuración inicial del host
### 1.1 Estructura base y red Docker
```bash
mkdir -p ~/srv/core ~/srv/projects
docker network create proxy_network
```
Permisos para usar Docker sin `sudo`:
```bash
sudo usermod -aG docker "$USER"
newgrp docker
```
### 1.2 Habilitar el script generador
```bash
chmod +x ~/srv/init_project.sh
```
---
## 2. Puesta en marcha del reverse proxy (`~/srv/core`)
### Opción A — Traefik (detección automática por etiquetas)
`~/srv/core/docker-compose.yml`:
```yaml
services:
traefik:
image: traefik:v3.0
container_name: core-proxy
restart: unless-stopped
security_opt:
- no-new-privileges:true
ports:
- "80:80"
- "443:443"
volumes:
- /etc/localtime:/etc/localtime:ro
- /var/run/docker.sock:/var/run/docker.sock:ro
- ./data/traefik.yml:/traefik.yml:ro
- ./data/acme.json:/acme.json
networks:
- proxy_network
networks:
proxy_network:
external: true
```
Configuración estática `~/srv/core/data/traefik.yml`:
```yaml
api:
dashboard: true
insecure: true
entryPoints:
web:
address: ":80"
websecure:
address: ":443"
providers:
docker:
endpoint: "unix:///var/run/docker.sock"
network: "proxy_network"
exposedByDefault: false
file:
filename: "/etc/traefik/dynamic_tls.yml"
watch: true
```
Inicialización del almacenamiento de certificados:
```bash
mkdir -p ~/srv/core/data
touch ~/srv/core/data/acme.json
chmod 600 ~/srv/core/data/acme.json
```
Arranque:
```bash
cd ~/srv/core && docker compose up -d
```
### Opción B — Nginx Proxy Manager (panel web)
Misma idea, pero la configuración se hace desde la interfaz:
1. Entrar a `http://<IP-SERVIDOR>:81`.
2. **Hosts → Proxy Hosts → Add Proxy Host**.
- **Domain Names:** `api.midominio.com`
- **Scheme:** `http`
- **Forward Hostname / IP:** nombre del contenedor en `proxy_network`
- **Forward Port:** puerto interno del contenedor
- **Block Common Exploits:** activado
3. Pestaña **SSL** → *Request a new SSL Certificate* → *Force SSL*.
4. **Save**.
---
## 3. Alta de proyectos
### Paso 1 — Crear la estructura limpia
```bash
~/srv/init_project.sh api-ventas api.midominio.com 80
```
Genera:
```text
~/srv/projects/api-ventas/
├── app/ # Código, repo o Dockerfile
├── data/
│ ├── db/
│ └── storage/
├── .env # Variables de entorno (chmod 600)
└── docker-compose.yml # Plantilla conectada a proxy_network
```
### Paso 2 — Colocar el proyecto
```bash
# Clonando un repositorio
git clone https://github.com/tu-usuario/api-ventas.git ~/srv/projects/api-ventas/app/
# O copiando archivos locales
cp -r /ruta/a/tus/archivos/* ~/srv/projects/api-ventas/app/
```
### Paso 3 — Ajustar `docker-compose.yml`
- **Build local:** descomentar
```yaml
build:
context: ./app
dockerfile: Dockerfile
```
- **Imagen ya publicada:** reemplazar `image: <proyecto>:latest`
- **Servicios adicionales** (Postgres, Redis): agregarlos en el mismo archivo
usando la red `default`, así quedan aislados del proxy.
### Paso 4 — Levantar
```bash
cd ~/srv/projects/api-ventas
docker compose up -d
```
### Paso 5 — Post-instalación (opcional, apps Laravel)
```bash
docker exec -it <proyecto>-web composer install --no-interaction --prefer-dist
docker exec -it <proyecto>-web php artisan key:generate --force
docker exec -it <proyecto>-web php artisan migrate --force
docker exec -it <proyecto>-web php artisan optimize:clear
```
Verificar permisos si el usuario `www-data` no puede escribir:
```bash
docker exec -it <proyecto>-web chown -R www-data:www-data /var/www/<app>/storage
docker exec -it <proyecto>-web chmod -R 775 /var/www/<app>/storage /var/www/<app>/bootstrap/cache
```
---
## 4. Dónde y cómo se registran las URLs
### Traefik (automático)
El registro se hace con **etiquetas** en el `docker-compose.yml` del proyecto:
```yaml
labels:
- "traefik.enable=true"
- "traefik.docker.network=proxy_network"
- "traefik.http.routers.api-ventas.rule=Host(`api.midominio.com`)"
- "traefik.http.routers.api-ventas.entrypoints=websecure"
- "traefik.http.routers.api-ventas.tls=true"
- "traefik.http.routers.api-ventas.tls.certresolver=letsencrypt"
- "traefik.http.services.api-ventas.loadbalancer.server.port=80"
```
Traefik lee el socket de Docker, detecta el contenedor, genera el enrutamiento y
solicita el certificado SSL automáticamente.
### Nginx Proxy Manager (panel web)
Ver [Opción B](#opción-b--nginx-proxy-manager-panel-web).
---
## 5. Copias de seguridad
Los respaldos se guardan **fuera** de los repositorios Git:
```bash
# PostgreSQL
docker exec <cont-pg> pg_dump -U <user> <db> > ~/srv/backups/<proyecto>-$(date +%F).sql
# MySQL
docker exec <cont-mysql> mysqldump -u<user> -p <db> > ~/srv/backups/<proyecto>-$(date +%F).sql
# Archivos
tar czf ~/srv/backups/<proyecto>-files-$(date +%F).tar.gz ~/srv/projects/<proyecto>/data
```
Sugerencia de rotación (crontab diario a las 3:00):
```cron
0 3 * * * /usr/local/bin/backup-proyectos.sh >> ~/srv/backups/backup.log 2>&1
```
---
## 6. Resumen de convenciones
| Elemento | Convención |
|---|---|
| Carpeta de proyecto | `~/srv/projects/<nombre>/` |
| Nombre del contenedor | `<nombre>-web` |
| Red del proxy | `proxy_network` (externa) |
| Red interna | `default` (bridge, aislada) |
| Secretos | `~/srv/projects/<nombre>/.env` con `chmod 600` |
| Dominios locales | `<proyecto>.local` |
| Certificados `.local` | `~/srv/core/data/certs/` + `dynamic_tls.yml` |
| Certificados públicos | Let's Encrypt vía `acme.json` |