Per the owner's spec: each social connection gets publishGovernance in its
fields — unset = manual publish (today), auto = dispatch on approval,
admin1/admin_majority/admin_consensus = a publish-phase chatgov poll
(subject draft_publish, its own open-poll slot, no collision with review
gates). Dispatch holds until the publish poll passes (E3 pre-dispatch
check); auto dispatches on approval. Includes migration 033, the PATCH
/connections/:id/publish-governance route (chatgov.manage), and 19+31 new
tests. Implementation by the branding-panel process (claude/opus), lint
and integration fixes here.
One-shot watcher for the workstation: probes ping.occupymedia.cc through a
reachable edge IP, flips the four hostnames after the port-forward verifies,
checks the public path for 6 minutes and auto-reverts to TUNNEL if the new
pool assignment is broken too. Retires itself if the tunnel heals first.
README updated to match.
Cloudflare's tunnel edge-pool assignment can blackhole the site for whole
regions (2026-10-10: tunnel hostnames served from an unreachable anycast
range for hours). This adds an independent path and the automation that
keeps occupymedia.cc reachable when either path is sick:
- nginx edge mirroring the tunnel ingress (app/api/tube/chat/ping), LE
wildcard via dns-01, twice-daily renewal
- DOCKER-USER firewall: 80/443 restricted to Cloudflare ranges (CF mode)
or OPEN for grey-cloud mode via firewall.mode
- edge-watcher (60s systemd timer): dynamic public-IP sync, dual-path
health checks, DNS failover TUNNEL<->ORIGIN/GREY with hysteresis,
gated by EDGE_ENABLED
- ping.occupymedia.cc sacrificial probe host for activation
- deployment runbook in README.md; credential files shipped as .example