From fbe81f9bf5f1ae7f2297161afc7062c82fdf36b2 Mon Sep 17 00:00:00 2001 From: oskar Date: Thu, 23 Jul 2026 18:27:51 +0200 Subject: [PATCH] =?UTF-8?q?docs(kb-query):=20ingress=20kb.kapala.org=20liv?= =?UTF-8?q?e=20=E2=80=94=20npm=20vhost=20+=20Pi-hole=20DNS,=20OIDC=20defer?= =?UTF-8?q?red?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Runtime steps (not in Git, logged here): npm@PIHA proxy host #35 (kb.kapala.org -> 192.168.31.5:8230, cert #49 *.kapala.org wildcard, same pattern as paper./vikunja.kapala.org); Pi-hole custom.list split-horizon entry added and verified (first kapala.org entry in that file — the other kapala.org vhosts turned out to have no LAN override at all, a plan assumption that didn't hold). Cloudflare A-record left for the operator (no API token available here). OIDC intentionally not built: confirmed no forward-auth pattern exists anywhere in this repo, and building authlib OIDC into kb-query is real service code out of scope for an infra-only task — operator decided to leave kb.kapala.org without auth for now. --- docs/sessions/2026-07-23-kb-f4-ingress.md | 113 ++++++++++++++++++++++ services/kb-query/README.md | 33 ++++++- 2 files changed, 144 insertions(+), 2 deletions(-) create mode 100644 docs/sessions/2026-07-23-kb-f4-ingress.md diff --git a/docs/sessions/2026-07-23-kb-f4-ingress.md b/docs/sessions/2026-07-23-kb-f4-ingress.md new file mode 100644 index 0000000..663e7fc --- /dev/null +++ b/docs/sessions/2026-07-23-kb-f4-ingress.md @@ -0,0 +1,113 @@ +# Sesja 2026-07-23 — KB faza 4: ingress kb.kapala.org (krok 5/§8) + +**Zakres**: wyłącznie ingress (`docs/kb/modules/05-faza4-plan.md` §8, krok 5) — +frontend i `/search` już LIVE na PIHA (port 8230) od sesji 2026-07-22. Zero +zmian w kodzie kb-query w tej sesji. + +## Zrobione + +### 1. Vhost npm@PIHA +`scripts/npm/npm_api.py --npm piha create-host --domain kb.kapala.org +--forward-host 192.168.31.5 --forward-port 8230 --cert-id 49 --ssl-forced +--http2-support --block-exploits --websocket --apply` → **proxy host #35**. +Parametry skopiowane 1:1 z `paper.kapala.org` (#33) po odczytaniu jego configu +przez API — `forward_scheme=http`, `access_list_id=0`, `caching_enabled=false`, +`advanced_config` puste (lekcja z `docs/sessions/2026-06-30-kapala-cloudflare-wildcard-mesh.md`: +`proxy_http_version` ręcznie w Advanced + Websockets ON = duplikat dyrektywy, +`nginx -t` odrzuca cały plik). Cert #49 = `*.kapala.org` wildcard, DNS-01 +Cloudflare, ważny do 2026-09-28 — **żaden nowy cert nie powstał**, zgodnie z +planem. + +### 2. Pi-hole split-horizon +Mechanizm: `/etc/pihole/custom.list` na PIHA (Pi-hole v5.18.4, natywny/systemd +`pihole-FTL`, nie kontener) — runtime, poza GitOps, dokładnie jak reszta +`~15` wpisów w tym pliku. Dodano `192.168.31.5 kb.kapala.org` + `pihole +restartdns`. Zweryfikowane: `dig kb.kapala.org @127.0.0.1` na PIHA i z hosta +LAN (SOLARIA, resolver = Pi-hole) → `192.168.31.5`. + +**Rozbieżność z założeniem planu** (STOP, wyjaśnione i zatwierdzone przez +operatora): zadanie zakładało "ten sam mechanizm co istniejące ~15 domen [dla +kapala.org]" — w rzeczywistości tych 15 wpisów to wyłącznie `*.okit.pl`, +**zero** istniejących `kapala.org` w `custom.list`. `paper./ha./immich./ +vikunja./forgejo.kapala.org` **nie mają** dziś override'u LAN — `dig` z PIHA i +z 8.8.8.8 zwracał identycznie `100.108.208.3` (Tailscale IP) dla +`paper.kapala.org`, czyli LAN-owy klient robi dziś hairpin przez Tailscale dla +wszystkich istniejących usług `kapala.org`. `kb.kapala.org` jest więc +**pierwszym** split-horizon wpisem dla tej domeny. Mechanizm (plik, komenda) +jest ten sam i poprawnie odtworzony — tylko przesłanka "już tak jest dla 15 +domen kapala.org" była błędna. Nie dotykano innych vhostów (poza zakresem) — +retrofit pozostałych `kapala.org` do LAN split-horizon to osobny, potencjalny +follow-up. + +### 3. Cloudflare A-record — częściowo poza tą sesją +Brak tokena Cloudflare API w środowisku wykonawczym. Operator dodaje ręcznie: +`kb.kapala.org` → `100.108.208.3` (Tailscale PIHA), DNS only — analogicznie do +`paper./ha./immich./vikunja./forgejo.kapala.org`. Bez tego rekordu +`kb.kapala.org` rozwiązuje się wyłącznie w LAN (Pi-hole); poza LAN (Tailscale) +nie zadziała, dopóki operator nie doda rekordu. Status: **do potwierdzenia +przez operatora**, nie zweryfikowane w tej sesji. + +### 4. OIDC — STOP wg instrukcji zadania +Potwierdzone w repo (zgodnie z `05-faza4-plan.md` §1.4): **brak wzorca +forward-auth/reverse-proxy-level auth** — NPM community edition go nie ma +(sprawdzone: brak `oauth2-proxy`/`authelia`/`forward_auth` w kodzie repo poza +wzmiankami "przyszła opcja" w `docs/kb/kb-02-documents-design.md` i +`hosts/vps/README.md`). Wszystkie 3 precedensy (paperless/nextcloud/vikunja) +robią OIDC **wewnątrz aplikacji**. kb-query nie ma dziś żadnego logowania. + +Zgodnie z instrukcją zadania: **nie budowano** nowego komponentu auth. +Zaproponowane operatorowi 2 opcje: +1. **Zostaw bez auth na razie** — `authlib` + `/login`/`/auth/callback` + wbudowane w kb-query (plan §8) to osobna sesja z kodem (~1 sesja szacunku + planu), poza zakresem tego zadania infra. +2. **Doraźny NPM Access List (Basic Auth)** — wbudowana funkcja NPM (wspólne + hasło na poziomie vhosta), zero kodu, zero nowego komponentu, ale to nie + SSO/Forgejo — tylko gate. + +**Decyzja operatora (2026-07-23): opcja 1** — `kb.kapala.org` zostaje bez auth +(LAN/Tailscale, jak dziś) do czasu osobnej sesji budującej `authlib` OIDC w +kb-query. Gotcha do pamięci na tamtą sesję (z Vikunja-precedensu): Forgejo +OAuth2 app wymaga **pełnego** redirect URI z kluczem providera +(`.../auth/callback` czy analogiczny, do potwierdzenia przy implementacji) — +niedokładny redirect URI w konfiguracji aplikacji OAuth to najczęstszy błąd +przy pierwszym logowaniu w tym repo (paperless miał podobny problem z +username collision, `docs/sessions/2026-07-10-paperless-deploy.md`). + +## Weryfikacja (DoD) + +- `curl -I` / `curl -v` przez `--resolve kb.kapala.org:443:192.168.31.5`: + `HTTP/2 200` na `/healthz`, cert `CN=*.kapala.org`, TLSv1.3, ważny do + 2026-09-28. +- `/search?q=test` przez vhost vs bezpośrednio na `192.168.31.5:8230`: + **identyczny** `envelope_id`/`dist`/`chunk_index`/`text` (ten sam kod, HTTP + to tylko opakowanie — zgodnie z kryterium bramki §9 planu, choć to nie jest + jeszcze formalny `retrieval_eval.py --transport http`, tylko ręczny + smoke-test tej sesji). +- Rozwiązywanie `kb.kapala.org` z hosta LAN (SOLARIA, resolver = Pi-hole) → + `192.168.31.5`, potwierdzone `dig`/`getent hosts`. +- Auth: brak (zgodnie z decyzją) — nic nie powinno wymagać logowania, i nic + nie wymaga (potwierdzone: `/search` i `/healthz` odpowiadają bez tokenu). + +## Stan na koniec sesji + +| Element | Status | +|---|---| +| npm@PIHA vhost #35 kb.kapala.org → 192.168.31.5:8230, cert 49 | ✅ LIVE | +| Pi-hole custom.list kb.kapala.org → 192.168.31.5 | ✅ LIVE (pierwszy kapala.org wpis) | +| Cloudflare A kb.kapala.org → 100.108.208.3 | ⏳ operator, ręcznie, nie zweryfikowane | +| OIDC | ⛔ świadomie odłożone — osobna sesja z kodem | + +## Pliki repo zmienione + +- `services/kb-query/README.md` — sekcja "Ingress" (co żyje, co nie, dlaczego + auth odłożone) zastępuje starą notatkę "not wired up yet". +- `docs/sessions/2026-07-23-kb-f4-ingress.md` — ten dokument. + +## Follow-upy (propozycje, nie w zakresie tej sesji) + +- Retrofit Pi-hole split-horizon dla `paper./ha./immich./vikunja./ + forgejo.kapala.org` (dziś wszystkie hairpinują przez Tailscale nawet z LAN) + — drobny, ale osobny task, nie dotykać przy okazji. +- `authlib` OIDC w kb-query (plan §8) — osobna sesja z kodem. +- `retrieval_eval.py --transport http` (plan §6 Decyzja 6, formalna bramka + HTTP-equivalence) — dziś tylko ręczny smoke-test, nie automat. diff --git a/services/kb-query/README.md b/services/kb-query/README.md index 04fb7d1..940c3e7 100644 --- a/services/kb-query/README.md +++ b/services/kb-query/README.md @@ -117,8 +117,37 @@ Frontend JS has its own pure-function tests (query-URL encoding, threshold colouring, envelope grouping), run without a browser via Node's built-in test runner: `node --test services/kb-query/tests/frontend/`. +## Ingress (`kb.kapala.org`, plan §8) + +Wired up 2026-07-23 (`docs/sessions/2026-07-23-kb-f4-ingress.md`), **no code +change in this service** — pure infra step: + +- npm@PIHA proxy host #35: `kb.kapala.org` → `http://192.168.31.5:8230`, + cert #49 (`*.kapala.org` wildcard, DNS-01 via Cloudflare, expires + 2026-09-28) — same pattern as `paper.`/`vikunja.`/`ha.kapala.org`. +- Pi-hole Local DNS (`/etc/pihole/custom.list` on PIHA, runtime, not in Git): + `kb.kapala.org` → `192.168.31.5`. **This is the first `kapala.org` entry in + that file** — every other `kapala.org` vhost (paper/ha/immich/vikunja/forgejo) + has no LAN override and resolves via the public Cloudflare record + (Tailscale IP) even from LAN, a hairpin the plan assumed was already avoided + for those too. Not fixed here (out of this task's scope — no other vhosts + touched); worth a follow-up if it matters for those services. +- Cloudflare A record `kb.kapala.org` → `100.108.208.3` (Tailscale PIHA, DNS + only): pending manual step by the operator (no CF API token available in + the environment that did this step) — without it, `kb.kapala.org` resolves + only on the LAN (Pi-hole), not over Tailscale from outside. + +**No auth.** OIDC (plan §8: `authlib`, `/login`, `/auth/callback`) is explicitly +**not implemented** — confirmed no forward-auth/reverse-proxy-level auth pattern +exists anywhere in this repo (NPM community edition doesn't support it either); +the three precedents (paperless/nextcloud/vikunja) all do OIDC inside the app. +Building that is real service code (`authlib` dependency, session middleware, +Forgejo OAuth2 app registration) — deliberately deferred to a separate session, +decision confirmed with the operator 2026-07-23. Until then `kb.kapala.org` is +reachable by anyone on the LAN/tailnet with no login, same as before this vhost +existed. + ## Out of scope for this step - Local-PIHA embed fallback / circuit breaker (plan §2 decision 2, §5). -- npm@PIHA vhost, OIDC login, DNS (plan §8) — `kb.kapala.org` is not wired up - yet; reach the API/UI directly over LAN/Tailscale for now, no auth. +- OIDC login (see above) — separate session, needs `authlib` + Forgejo OAuth2 app.