# Admin (openbureau-core CMS) The site is edited through **openbureau-core** — a small Node CMS (vendored at `cms/core`) that builds the Hugo site and serves it together with an editor at `/admin`. It is **DB-less**: file-based login (`auth: 'local'`) and Markdown on disk. No Supabase, no Postgres. ## What's where - `cms/kgva.config.js` — the content model (collections + fields) the editor renders. - `cms/core/` — the engine (git subtree of `git.openbureau.ch/karim/openbureau-core`). Update it with: `git subtree pull --prefix=cms/core https://git.openbureau.ch/karim/openbureau-core.git main --squash` - `cms/.env` — `JWT_SECRET` (sign-in secret) + `ADMIN_EMAILS`. Copy from `.env.example`. - `cms/users.json` — the user store (bcrypt hashes). Git-ignored. Seed with: `docker compose run --rm cms node /site/cms/seed-admin.mjs you@mail yourpass` ## Run ``` cp cms/.env.example cms/.env # set JWT_SECRET (openssl rand -hex 32) docker compose build docker compose run --rm cms node /site/cms/seed-admin.mjs karim@gabrielevarano.ch # once docker compose up -d ``` Open `http://:8080/admin/`, log in, edit. *Speichern* writes the Markdown, *Vorschau* builds a draft preview, *Publizieren* rebuilds the public site. ## Deploy A single container (Hugo build + Node serve). See `deploy/` — `provision-lxc.sh` stands up an LXC and does all of the above (incl. a seeded admin whose password lands in `cms/ADMIN_PASSWORD.txt`); `Caddyfile` terminates TLS and reverse-proxies the domain. Safe cutover: provision a NEW container on a temporary IP, verify, point Caddy at it, then retire the old one.