Actualiza toolkit operativo y documentación
This commit is contained in:
@@ -0,0 +1,78 @@
|
||||
# OpenSEO self-host — Coolify stack (LXC 102)
|
||||
#
|
||||
# Por qué este compose en lugar del repo upstream (`every-app/open-seo`) vía
|
||||
# railpack:
|
||||
# - el deploy anterior (uuid kj0kccsb4d46tm0d6qe6docy) terminó con Caddy
|
||||
# respondiendo 404 a todo porque /app/dist no existía en la imagen cacheada
|
||||
# (Coolify saltó el build: "No build configuration changed & image found ...
|
||||
# Build step skipped").
|
||||
# - el README upstream lo dice explícitamente: "We recommend self-hosting
|
||||
# with Cloudflare as opposed to Railway, Coolify or Dokploy. We plan to
|
||||
# make it simpler to host on those platforms in the next few months."
|
||||
# - esta imagen (`ghcr.io/every-app/open-seo:sha-c469a48`) es la build del
|
||||
# mismo commit, pero el build de Vite corre en `docker-entrypoint.sh` al
|
||||
# arrancar el contenedor, no en el build de la imagen. Y el entrypoint ya
|
||||
# tiene la lógica de fingerprint para no reconstruir cuando los env vars
|
||||
# relevantes no cambiaron.
|
||||
#
|
||||
# Contrato: docs/AGENTS-coolify-apps.md
|
||||
# - sin publicar 80/443: solo `expose`, Traefik enruta (§2.3)
|
||||
# - SECRETOS vía env vars inyectados por Coolify (§2.5)
|
||||
# - volumen con nombre para /app/.wrangler (SQLite que sobrevive al redeploy, §5)
|
||||
# - healthcheck independiente de servicios externos al boot
|
||||
# - AUTH_MODE=local_noauth porque aquí no hay TEAM_DOMAIN/POLICY_AUD de
|
||||
# Cloudflare Access. Si más adelante se quiere proteger con auth, cambiar
|
||||
# a AUTH_MODE=cloudflare_access + TEAM_DOMAIN + POLICY_AUD.
|
||||
# - ALLOWED_HOST es obligatorio detrás del túnel: sin él Vite bloquea toda
|
||||
# petición externa con "Blocked request" (ver preflight info level).
|
||||
|
||||
services:
|
||||
app:
|
||||
image: 'ghcr.io/every-app/open-seo:sha-c469a48'
|
||||
environment:
|
||||
# Puerto en el que escucha `vite preview` (per Dockerfile.selfhost / entrypoint).
|
||||
- PORT=3001
|
||||
# Single admin user, sin pantalla de login. NO exponer públicamente sin
|
||||
# poner tu propia auth delante — el preflight lo dice literal.
|
||||
- AUTH_MODE=local_noauth
|
||||
# Host header permitido. Es el FQDN público por el que llega el tráfico
|
||||
# desde el túnel de Cloudflare.
|
||||
- ALLOWED_HOST=openseo.urieljareth.org
|
||||
# Requerido por el runtime workerd para exponer process.env a los
|
||||
# bindings (lo exige el compose upstream).
|
||||
- CLOUDFLARE_INCLUDE_PROCESS_ENV=true
|
||||
# SEO data (opcional). Vacío = la app arranca, los workflows SEO
|
||||
# devuelven "no data". Se setea después vía Coolify env.
|
||||
- DATAFORSEO_API_KEY=${DATAFORSEO_API_KEY:-}
|
||||
# Telemetry opt-out (también vía DO_NOT_TRACK). Por defecto apagado.
|
||||
- OPENSEO_TELEMETRY_DISABLED=${OPENSEO_TELEMETRY_DISABLED:-}
|
||||
- DO_NOT_TRACK=${DO_NOT_TRACK:-}
|
||||
# AI features (SAM, el agente SEO integrado). Vacío = SAM deshabilitado.
|
||||
- OPENROUTER_API_KEY=${OPENROUTER_API_KEY:-}
|
||||
- OPENROUTER_MODEL=${OPENROUTER_MODEL:-}
|
||||
expose:
|
||||
- '3001'
|
||||
# El endpoint /api/health lo sirve el propio preflight (ver
|
||||
# src/lib/selfhost-preflight.ts) sin auth — seguro para el healthcheck.
|
||||
# Usamos `node` directamente porque la imagen es node:22 y el HEALTHCHECK
|
||||
# upstream hace exactamente esto.
|
||||
healthcheck:
|
||||
test:
|
||||
- CMD-SHELL
|
||||
- "node -e \"fetch('http://127.0.0.1:3001/api/health').then(r=>process.exit(r.ok?0:1)).catch(()=>process.exit(1))\""
|
||||
interval: 30s
|
||||
timeout: 10s
|
||||
retries: 5
|
||||
# Primer arranque: preflight + migrations + vite build (1-2 min).
|
||||
start_period: 300s
|
||||
volumes:
|
||||
- 'openseo-data:/app/.wrangler'
|
||||
restart: unless-stopped
|
||||
logging:
|
||||
driver: json-file
|
||||
options:
|
||||
max-size: '10m'
|
||||
max-file: '3'
|
||||
|
||||
volumes:
|
||||
openseo-data: {}
|
||||
Reference in New Issue
Block a user