# books-ssh-audit-shared-vds ## Goal SSH-аудит на shared VDS (`vds.kzntsv.site` / 89.253.255.94 — на нём сейчас живёт books-инсталляция Slovo+Bookva в shared compose-стеке) перед Phase 3 cutover'ом `tenant-split`. Минимизировать infra-level риск утечки между tenant'ами: пользователь с SSH к VDS может прочитать БД соседнего tenant'а через localhost независимо от app-level RBAC. См. `victor/books/.wiki/concepts/tenant-split.md` §«Двухуровневая изоляция пользователей → Infra-level». ## Key files - `[[../entities/vds-kzntsv]]` — host entity (89.253.255.94 / vds.kzntsv.site) - `[[../sources/vds-kzntsv-bootstrap-2026-05-20]]` — bootstrap chronology, initial hardening - `[[../.wiki/concepts/books-ssh-access.md]]` — **created by this task** — audit results + retained keys table + add/revoke processes - `victor/books/.wiki/concepts/tenant-split.md` — design context (dev-source) ## Decisions log - **2026-05-24 (initial audit run):** dumped `/home/vitya/.ssh/authorized_keys` + `/root/.ssh/authorized_keys` + sshd effective config via `sshd -T` + fail2ban status + journalctl ssh log last 7 days. Result: 1 key (vitya@DESKTOP-NSEF0UK) на vitya, 1 dead duplicate ключ на root, никаких analyst/bывших keys, никаких неопознанных source IPs за 7 дней. - **2026-05-24 (cleanup):** удалил dead key из `/root/.ssh/authorized_keys` (truncate). Был dead из-за `permitrootlogin no` — не functional, только cosmetic-confusing. Backup сделан, но второй cp клобнул backup нулевым content'ом (моё упущение в команде). Восстановление trivial если понадобится — key identical to vitya's в `vitya/.ssh/authorized_keys`. - **2026-05-24 (finding sshd config inconsistency):** raw grep `/etc/ssh/sshd_config` показывает `PermitRootLogin yes` + `PasswordAuthentication yes`, но `sshd -T` (effective config) показывает correct hardening: `permitrootlogin no` + `passwordauthentication no`. Override'ы в `/etc/ssh/sshd_config.d/*.conf` или cloud-init drop-in делают finальный config. **Future audits должны проверять через `sshd -T`, не плоский grep.** Это зафиксировано в `concepts/books-ssh-access.md` §«sshd hardening state». ## Open questions (none — все решены в audit) ## Completed steps - [x] **2026-05-24 ~15:53:** SSH audit run на vds-kzntsv: - `cat /home/vitya/.ssh/authorized_keys` → 1 key (`vitya@DESKTOP-NSEF0UK`) - `getent passwd` → 2 users with shell: root + vitya (минимум, ожидаемо) - `sudo cat /root/.ssh/authorized_keys` → 1 dead duplicate key (root SSH disabled) - `sudo systemctl is-active fail2ban` → active; 2670 failed / 37 banned (currently 0) — adequate - `sudo journalctl -u ssh ... | grep Accepted` → только vitya@94.19.247.14 last 7 days - `sudo sshd -T | grep ...` → correct hardening (permitrootlogin/passwordauth/kbd = no) - [x] **2026-05-24 ~15:55:** removed dead key из `/root/.ssh/authorized_keys` via `sudo bash -c ': > /root/.ssh/authorized_keys'`. File now empty (0 bytes). - [x] **2026-05-24:** documentation written → `.wiki/concepts/books-ssh-access.md` (retained keys table + sshd state + fail2ban + login history + add/revoke processes + cross-refs). ## Closed **2026-05-24** — audit clean, нечего revoke'ать кроме cosmetic dead root key. Тенант-split Phase 3 §SSH-аудит acceptance ✅: - ✅ `~/.ssh/authorized_keys` reviewed — 1 key (vitya, core dev) - ✅ Non-core keys revoked — N/A (none existed) - ✅ Analyst keys revoked — N/A (none existed) - ✅ Documented in `.wiki/concepts/books-ssh-access.md` **Closes** Фаза 3, шаг 2 `tenant-split` design. ## Notes - **Single-developer / single-key environment** — на этой машине я единственный человек, у которого SSH. Это упрощает audit dramatically. После Phase 4 (когда Bookva уедет на отдельный VDS) — каждая box будет под SSH своей "команды" (которая для нашего setup = me, но formal-administrator-of-bookva от учредителя Bookva может быть добавлен — process в `books-ssh-access.md` §«How to add a new key»). - **Bootstrap claim audit:** `[vds-kzntsv-bootstrap]` 🟢 close-note сказал «hardened sshd (key-only)». Verified through `sshd -T` — claim true, но raw `/etc/ssh/sshd_config` misleading (default pkg config). Если ещё кто-то будет верифицировать → `sshd -T` always. - **Atomic revert:** ничего материального не сделано revoke (только cosmetic empty root-keys). Если понадобится — `ssh vitya@89.253.255.94 'echo "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIKwYw1sS0Dj5FQmNxqJUV9IxU+9hZcg8qYQRgLN5ER/Z vitya@DESKTOP-NSEF0UK" | sudo tee /root/.ssh/authorized_keys'`.