diff --git a/scripts/farm/cosecha-cron.sh b/scripts/farm/cosecha-cron.sh index b56f6db4..5c63489b 100755 --- a/scripts/farm/cosecha-cron.sh +++ b/scripts/farm/cosecha-cron.sh @@ -64,6 +64,16 @@ fi SSH_KEY="${SSH_KEY:-$HOME/.ssh/github5}" REMOTE="${REMOTE:-/opt/hammer}" FLEET="$ROOT/scripts/farm/.fleet" +# ── SIEMBRA DE LA FLOTA FIJA ──────────────────────────────────────────────────────────────────── +# `.fleet` es estado de EJECUCIÓN (gitignored, lo reescribe el reaper cada ciclo); `flota-permanente` +# es la parte versionada. Sin esto, un hub recién clonado nace con la flota vacía y la granja queda +# desconectada EN SILENCIO: «flota vacía» cada 30 min, los artefactos del worker no vuelven, y nada +# falla. Se unen por NOMBRE (el fijo gana) para que lo efímero de hcloud conviva sin duplicarse. +FLEET_FIJA="$ROOT/scripts/farm/flota-permanente" +if [ -s "$FLEET_FIJA" ]; then + { grep -vE '^[[:space:]]*(#|$)' "$FLEET_FIJA"; cat "$FLEET" 2>/dev/null; } \ + | awk 'NF && !visto[$1]++' > "$FLEET.seed" && mv "$FLEET.seed" "$FLEET" +fi HAMMER="${HAMMER:-$ROOT/target/release/hammer}" # Workers efímeros reciclan IPs ⇒ no fijar known_hosts (hub-and-spoke, worker sin secretos). SSH="ssh -i $SSH_KEY -o UserKnownHostsFile=/dev/null -o StrictHostKeyChecking=no -o BatchMode=yes -o LogLevel=ERROR -o ConnectTimeout=15" @@ -361,7 +371,11 @@ fi if [ "${NO_COMMIT:-}" != "1" ]; then git add docs/state/sonames.txt docs/state/build-state.json docs/state/build-state-kde.json docs/state/build-state-gnome.json docs/state/build-state-cosmic.json docs/state/build-state-wlr.json docs/state/drenaje.json docs/state/fuentes-vigia.json docs/state/kernel-contract.txt docs/state/static-audit.txt 2>/dev/null || true if ! git diff --cached --quiet 2>/dev/null; then - git commit -q -m "estado: cosecha granja $(ts) — avance del árbol KDE" 2>/dev/null \ + # ⚠ ACOTADO POR PATHSPEC (`-- `), no sólo por el `git add` de arriba: el índice es + # estado COMPARTIDO y `git commit` a secas commitea el índice ENTERO, así que lo que otro + # agente dejara en `git add` viajaría dentro del commit del cron. Es la regla 2 de CLAUDE.md, + # y acá pesa más que en ningún lado: esto corre desatendido cada 30 min mientras se trabaja. + git commit -q -m "estado: cosecha granja $(ts) — avance del árbol KDE" -- docs/state/sonames.txt docs/state/build-state.json docs/state/build-state-kde.json docs/state/build-state-gnome.json docs/state/build-state-cosmic.json docs/state/build-state-wlr.json docs/state/drenaje.json docs/state/fuentes-vigia.json docs/state/kernel-contract.txt docs/state/static-audit.txt 2>/dev/null \ && { git push -q origin main 2>/dev/null && echo "==> estado commiteado+pusheado" \ || echo "==> estado commiteado (push falló, reintenta próximo ciclo)"; } else diff --git a/scripts/farm/flota-permanente b/scripts/farm/flota-permanente new file mode 100644 index 00000000..51b4f68b --- /dev/null +++ b/scripts/farm/flota-permanente @@ -0,0 +1,15 @@ +# flota-permanente — los workers FIJOS de la granja, versionados. +# +# POR QUÉ EXISTE (2026-09-08). `scripts/farm/.fleet` está en `.gitignore` y con razón: los workers +# efímeros de hcloud entran y salen, y el reaper lo REESCRIBE en cada ciclo. Pero eso tenía un coste +# que nadie había pagado todavía: **un hub recién clonado nacía con la flota VACÍA y la granja +# quedaba desconectada EN SILENCIO** — `cosecha-cron` decía «flota vacía» cada 30 min, los +# artefactos del worker no volvían nunca, `estado-granja.sh` reportaba «no hay worker vivo» con el +# worker compilando, y NADA fallaba. Así se descubrió, por casualidad. +# +# Este fichero es la parte que SÍ debe sobrevivir a un clon: los workers permanentes. `cosecha-cron` +# siembra `.fleet` desde acá al empezar cada ciclo (unión sin duplicar por nombre), así que lo +# efímero sigue viviendo sólo en `.fleet` y lo fijo se repone solo. +# +# Formato: · líneas en blanco y `#` se ignoran. +dev.gioser.net 154.197.1.13