id: cfe2a1f1db894f6f89716ae3e298b8f1
parent_id: 0609d89ff61e436b993746ca7b11a2e8
item_type: 1
item_id: a69d84030b1742ffb63ff3248a02cb92
item_updated_time: 1787991864040
title_diff: "[]"
body_diff: "[{\"diffs\":[[0,\"8-29\"],[-1,\", topology corrected same day after grounding the git\\\n> remotes; private-repo policy and jail/privilege model added 2026-08-29.\\\n>\"],[1,\". **FreeBSD Forgejo: INSTALLED 2026-08-29 (see \\\"Forgejo on\\\n> moria — Installation Record\\\").** Hetzner work still pending.\"],[0,\" Mis\"]],\"start1\":67,\"start2\":67,\"length1\":137,\"length2\":129},{\"diffs\":[[0,\"n: audit\"],[1,\"\\\n>\"],[0,\" the Het\"]],\"start1\":199,\"start2\":199,\"length1\":16,\"length2\":18},{\"diffs\":[[0,\"t up the\"],[-1,\"\\\n>\"],[0,\" contain\"]],\"start1\":254,\"start2\":254,\"length1\":18,\"length2\":16},{\"diffs\":[[0,\"orm \"],[-1,\"(reverse proxy, Forgejo role per below, optionally\\\n> Jenkins) —\"],[1,\"—\\\n>\"],[0,\" **i\"]],\"start1\":278,\"start2\":278,\"length1\":71,\"length2\":11},{\"diffs\":[[0,\"ment\"],[-1,\"\\\n>\"],[0,\" server\"],[1,\"\\\n>\"],[0,\" (19\"]],\"start1\":341,\"start2\":341,\"length1\":17,\"length2\":17},{\"diffs\":[[0,\".168.1.2\"],[1,\", moria\"],[0,\") is the\"]],\"start1\":359,\"start2\":359,\"length1\":16,\"length2\":23},{\"diffs\":[[0,\" is the \"],[-1,\"current \"],[0,\"canonica\"]],\"start1\":375,\"start2\":375,\"length1\":24,\"length2\":16},{\"diffs\":[[0,\" hub\"],[-1,\" running Jenkins on\\\n> bare repos\"],[0,\"; Co\"]],\"start1\":396,\"start2\":396,\"length1\":40,\"length2\":8},{\"diffs\":[[0,\"anual public\"],[1,\"\\\n>\"],[0,\" mirror for \"]],\"start1\":417,\"start2\":417,\"length1\":24,\"length2\":26},{\"diffs\":[[0,\"ture\"],[-1,\" (DECIDED direction 2026-08-29)\"],[0,\":**\\\n\"]],\"start1\":987,\"start2\":987,\"length1\":39,\"length2\":8},{\"diffs\":[[0,\" binary)\"],[1,\"  [INSTALLED]\"],[0,\"\\\n       \"]],\"start1\":1063,\"start2\":1063,\"length1\":16,\"length2\":29},{\"diffs\":[[0,\"``\\\n\\\n\"],[-1,\"- **Forgejo on FreeBSD = CANONICAL, not a mirror**: import the bare repos\\\n  into it (create repo → push the bare repo in → set push mirrors out).\\\n  Web UI + auth for what is already the origin; push mirrors AUTOMATE the\\\n  current manual Codeberg dual-push\\\n- **Hetzner = private pull-side/backup + Linux CI**: mirror target and the\\\n  only place Actions runners with containers can live\\\n- **Jenkins stays on FreeBSD** (native, already working); migrate jobs to\\\n  Actions only if/when it earns it — re-point existing jobs to Forgejo URLs\\\n  after the repo import\\\n\\\n**Private-repo mechanics (confirmed 2026-08-29):** per-repo visibility in\\\nForgejo (private/public at creation, toggleable in Settings or API\\\n`private: true`); set `DEFAULT_PRIVATE = true` in app.ini so public becomes\\\nthe explicit choice; deploy keys/tokens cover Jenkins, mirrors, agents.\\\nPush mirrors from private sources are fine — visibility is per instance, so\\\nthe private repos mirror to Hetzner only.\\\n\\\n**Forgejo jail & privilege model (DECIDED 2026-08-29):** Forgejo runs as an\\\nUNPRIVILEGED `forgejo` user inside a service jail (Bastille or plain\\\njail.conf; ZFS dataset per jail if ZFS). Host root/doas only manages the\\\njail; root inside the jail only for pkg administration; the daemon never\\\nruns as root. Jail networking = IP alias on the LAN interface (own address,\\\ngit-SSH on its port 22, no VNET needed); jail.conf hardening: restrictive\\\ndevfs_ruleset, allow.raw_sockets=0, exec_clean, autostart. Rationale: the\\\nbox also runs Jenkins and the SSH path for ALL canonical repos — containment\\\nlimits compromise blast radius to one jail. Install: check `pkg search\\\nforgejo` / ports first (www/gitea exists for sure); worst case build from\\\nsource (Go compiles natively). Jenkins: host for now, own jail later if\\\nwant\"],[1,\"## FreeBSD corrections\\\n\\\n- No Docker on FreeBSD: container platform on Hetzner only; jails here\\\n- Joplin desktop on FreeBSD: unverified; MCP host fallback = Hetzner or Windows\\\n- Kilo CLI / Java (PD) on FreeBSD: unverifi\"],[0,\"ed\"],[-1,\".\"],[0,\"\\\n\\\n## \"],[-1,\"FreeBSD corrections (to earlier advice — important)\\\n\\\n- **No Docker on FreeBSD**: the container platform lives on Hetzner only.\\\n  FreeBSD containment = jails; Forgejo runs as the native Go binary (in a\\\n  jail), no containers needed\\\n- **Joplin desktop on FreeBSD: unverified** (Electron — ports/Linuxulator\\\n  unclear). If it doesn't run cleanly, the MCP host moves to Hetzner (Linux)\\\n  or stays on Windows — decide when wiring the server agents\\\n- Kilo CLI (Node) and Java (PD) should run on FreeBSD, but both unverified —\\\n  test before relying on them there\\\n\\\n## Phase 0 — Access & agent placement\\\n\"],[1,\"Phase 0 — Access & agent placement\\\n\\\n- [x] FreeBSD box: agent access via SSH (proven — git pushes + full install)\"],[0,\"\\\n- [\"]],\"start1\":1440,\"start2\":1440,\"length1\":2392,\"length2\":345},{\"diffs\":[[0,\"CLI \"],[-1,\"directly \"],[0,\"on t\"]],\"start1\":1802,\"start2\":1802,\"length1\":17,\"length2\":8},{\"diffs\":[[0,\" box\"],[-1,\" (recommended for the audit);\\\n     \"],[1,\";\"],[0,\" SSH\"]],\"start1\":1812,\"start2\":1812,\"length1\":43,\"length2\":9},{\"diffs\":[[0,\" to \"],[-1,\"whichever host ends up running\\\n      the MCP server (see above — FreeBSD feasibility open)\\\n- [ ] FreeBSD box: agent access via SSH (already proven — git pushes)\\\n\\\n## Phase 1 — Audit (evidence-first, like the keyfob gate)\\\n\\\n- [ ] System inventory: OS, kernel, uptime, CPU/RAM/disk, virtualization\\\n- [ ] Service inventory: enabled units, listeners, timers (+ FreeBSD side:\\\n      Jenkins, sshd, anything else on 192.168.1.2)\\\n- [ ] Security posture: SSH config, firewall state, fail2ban,\\\n      unattended-upgrades, users/keys, Docker daemon exposure\\\n- [ ] Performance: top consumers, disk usage + I/O, journal size, swap\\\n- [ ] Docker hygiene: containers/images/volumes, prune candidates\"],[1,\"the MCP host (decision pending)\\\n\\\n## Phase 1 — Audit\\\n\\\n- [ ] Hetzner: system/service/security/performance/Docker audit (evidence report)\\\n- [ ] FreeBSD side: partial picture from install (jails now exist, ZFS layout known);\\\n      full audit optional\"],[0,\"\\\n- [\"],[-1,\" ] Backups: what exists, what's missing — **including the bare repos on\\\n      FreeBSD (currently the single point of failure for ALL active repos!)**\"],[1,\"x] Repo backup gap identified — closure = Forgejo import + Hetzner mirror\"],[0,\"\\\n- [\"]],\"start1\":1870,\"start2\":1870,\"length1\":841,\"length2\":331},{\"diffs\":[[0,\"ort \"],[-1,\"committed to\"],[1,\"in\"],[0,\" the\"]],\"start1\":2226,\"start2\":2226,\"length1\":20,\"length2\":10},{\"diffs\":[[0,\"tune\"],[-1,\" (per audit findings)\\\n\\\n- [ ] Firewall (default deny; SSH/proxy ports only), SSH hardening,\\\n      unattended-upgrades, fail2ban (Hetzner)\\\n- [ ] Performance fixes from findings\"],[1,\"\\\n\\\n- [ ] Hetzner firewall/SSH/fail2ban/updates per audit\"],[0,\"\\\n- [\"]],\"start1\":2271,\"start2\":2271,\"length1\":182,\"length2\":63},{\"diffs\":[[0,\" closure\"],[-1,\":\"],[1,\" via\"],[0,\" Forgejo\"]],\"start1\":2348,\"start2\":2348,\"length1\":17,\"length2\":20},{\"diffs\":[[0,\"rror\"],[-1,\" removes the\\\n      single-copy risk for the repos\"],[0,\"\\\n\\\n##\"]],\"start1\":2388,\"start2\":2388,\"length1\":57,\"length2\":8},{\"diffs\":[[0,\"\\\n- [\"],[-1,\" ] Hetzner: reverse proxy with TLS (Caddy/Traefik) first\\\n- [ ] FreeBSD: Forgejo service jail per the privilege model ab\"],[1,\"x] FreeBSD: Forgejo jail INSTALLED and verified (2026-08-29) — see install record\\\n- [ ] Repo import into Forgejo (git push --mirror per repo; old bare repos stay\\\n      as fallback until cut-\"],[0,\"ove\"],[1,\"r\"],[0,\"; \"],[-1,\"import\\\n      bare repos; set p\"],[1,\"dev-machine remotes re-pointed at\\\n      192.168.1.10; keyfob + super-marvin created PRIVATE)\\\n- [ ] P\"],[0,\"ush \"]],\"start1\":2453,\"start2\":2453,\"length1\":162,\"length2\":304},{\"diffs\":[[0,\" mirrors\"],[1,\":\"],[0,\" \"],[-1,\"(\"],[0,\"Codeberg\"]],\"start1\":2756,\"start2\":2756,\"length1\":18,\"length2\":18},{\"diffs\":[[0,\"-in \"],[-1,\"per repo; keyfob +\\\n      super-marvin private → Hetzner mirror only)\\\n- [ ] Hetzner:\"],[1,\"(rusty_emu, top_drives); Hetzner for all\\\n- [ ] Hetzner: reverse proxy + TLS,\"],[0,\" For\"]],\"start1\":2778,\"start2\":2778,\"length1\":91,\"length2\":84},{\"diffs\":[[0,\"Forgejo \"],[-1,\"as \"],[0,\"mirror t\"]],\"start1\":2859,\"start2\":2859,\"length1\":19,\"length2\":16},{\"diffs\":[[0,\"rget\"],[-1,\" (private);\"],[1,\",\"],[0,\" Act\"]],\"start1\":2876,\"start2\":2876,\"length1\":19,\"length2\":9},{\"diffs\":[[0,\"ers\\\n\"],[-1,\"      (container-capable) — Jenkins vs Actions decision per\"],[1,\"- [ ] Jenkins:\"],[0,\" re\"],[1,\"-\"],[0,\"po\"],[-1,\", not global\\\n- [ ] Non-public services bound to localhost/WireGuard only\"],[1,\"int to Forgejo URLs after import\"],[0,\"\\\n\\\n##\"]],\"start1\":2894,\"start2\":2894,\"length1\":144,\"length2\":60},{\"diffs\":[[0,\"epo:\"],[-1,\" compose +\"],[0,\" jai\"]],\"start1\":3008,\"start2\":3008,\"length1\":18,\"length2\":8},{\"diffs\":[[0,\"configs \"],[1,\"+ compose \"],[0,\"in git; \"]],\"start1\":3018,\"start2\":3018,\"length1\":16,\"length2\":26},{\"diffs\":[[0,\"ases\"],[-1,\" = deployable\"],[0,\"\\\n- [\"]],\"start1\":3055,\"start2\":3055,\"length1\":21,\"length2\":8},{\"diffs\":[[0,\"note\"],[-1,\" in Joplin;\"],[0,\" link\"],[1,\"ed\"],[0,\" fro\"]],\"start1\":3073,\"start2\":3073,\"length1\":24,\"length2\":15},{\"diffs\":[[0,\"ndex\"],[-1,\"\\\n- [ ] PSP logging optional for infra work (agent-captured if desired)\"],[0,\"\\\n\\\n##\"]],\"start1\":3116,\"start2\":3116,\"length1\":78,\"length2\":8},{\"diffs\":[[0,\"ants\"],[-1,\" (public server!)\"],[0,\"\\\n\\\n- \"]],\"start1\":3140,\"start2\":3140,\"length1\":25,\"length2\":8},{\"diffs\":[[0,\"repos\\\n- \"],[-1,\"**\"],[0,\"Private \"]],\"start1\":3303,\"start2\":3303,\"length1\":18,\"length2\":16},{\"diffs\":[[0,\"station \"],[-1,\"and\"],[1,\"+\"],[0,\" super-m\"]],\"start1\":3333,\"start2\":3333,\"length1\":19,\"length2\":17},{\"diffs\":[[0,\"in (\"],[-1,\"whole \"],[0,\"poke\"]],\"start1\":3353,\"start2\":3353,\"length1\":14,\"length2\":8},{\"diffs\":[[0,\" line) —\"],[-1,\"\\\n \"],[0,\" LAN + p\"]],\"start1\":3362,\"start2\":3362,\"length1\":18,\"length2\":16},{\"diffs\":[[0,\" private\"],[1,\"\\\n \"],[0,\" Hetzner\"]],\"start1\":3376,\"start2\":3376,\"length1\":16,\"length2\":18},{\"diffs\":[[0,\"rges\"],[-1,\", no Codeberg\\\n  mirrors; DEFAULT_PRIVATE=true on both Forgejo instances**\"],[1,\"; DEFAULT_PRIVATE=true (set)\"]],\"start1\":3423,\"start2\":3423,\"length1\":77,\"length2\":32}]"
metadata_diff: {"new":{},"deleted":[]}
encryption_cipher_text: 
encryption_applied: 0
updated_time: 2026-08-29T08:29:35.195Z
created_time: 2026-08-29T08:29:35.195Z
is_locked: 0
type_: 13