17 KiB
Admin Task Board
Updated: 2026-05-24 (Cleanup: 25 🟢 closed blocks → ARCHIVE.md; per-task .md остаются in-place. Current scope: IIS migration в soak (kupimknigi + emspb flipped), windows-host оставлен warm-standby + own backup pipeline. Tandemmebel.ru остаётся на windows-IIS отдельно.)
🟡 [iis-migration-to-ruvds] — RUVDS IIS live для 2 prod hostnames (kupimknigi + emspb flipped); 22 в очереди. tandemmebel.ru остаётся на windows-IIS отдельно. Source held для rollback.
Status: in_progress (DNS partial cutover — soak window 2026-05-24)
Where I stopped: 2026-05-24 — kupimknigi.spb.ru + emspb.ru (+ www.emspb.ru) DNS A flipped на 80.64.31.36, authoritative ns1.reg.ru правильный, public resolver caches expire'ятся (8.8.8.8=~6h, 1.1.1.1=~24h max). RUVDS state: snolla site (8.66 GB / 44725 files) transferred + IIS recreated + 25 HTTPS SNI bindings c LE certs (R13, valid до 2026-07-22), 7 prod hostnames live-smoke через VDS (третья сеть) → 200 OK / correct content. Source IIS:8089 + traefik routes ALIVE — rollback ready.
Findings зафиксированы в iis-migration-to-ruvds.md Decisions log: (1) outbound 445 блокирует home ISP, не RUVDS-FW → SSH/scp = canonical transfer-метод; (2) home network HTTP-middlebox mangles Host header for direct external HTTP — real end-users не пострадают, тестировать через VDS; (3) traefik acme.json → IIS PFX recipe работает (extract + openssl pkcs12 -export + Import-PfxCertificate + AddSslCertificate by thumbprint); (4) IIS 10 HTTP/2 default; (5) maljarka.tandemmebel.ru + 3 rimiz hostnames → 502/404 — pre-existing CMS-tenant config gap, не migration defect.
Scope exception (2026-05-24 user decision): tandemmebel.ru + www.tandemmebel.ru ОСТАЮТСЯ на windows-IIS на неопределённый срок (отдельное решение user'а — site не готов к cutover ровно сейчас). DNS НЕ свапать. Cert на RUVDS уже импортирован, binding existing — может оставаться idle, traffic не пойдёт.
Next action:
- Снизить DNS TTL в reg.ru на оставшиеся 22 hostnames до 300s —
pilorama98.ru,labtools.{ru,pro},snolla.com+ 11 snolla subdomains +rimiz.{ru,snolla.com}+maljarka.tandemmebel.ru(но неtandemmebel.ru— см. Scope exception). Сократит cache-tail с 24h до 5 мин. - 24h soak kupimknigi + emspb — verify через cache-clean resolver (потом curl без
--resolve). - Bulk DNS swap оставшихся 22 hostnames на 80.64.31.36 (single sitting). tandemmebel.ru / www.tandemmebel.ru — пропустить.
- 1-week prod soak с RUVDS как live source для migrated hostnames.
- Decommission source IIS:8089 только для migrated hostnames (snolla catch-all site нельзя decommission'ить пока tandemmebel.ru на нём же). Решение defer до tandemmebel migration.
- LE renewal pipeline — win-acme + HTTP-01 на RUVDS после full cutover (LE certs expire 2026-07-22, soak window до ~07-15).
- Cleanup migration-temp:
Remove-NetFirewallRule 'smb-from-source','ssh-from-source'на RUVDS, удалить~/.ssh/ruvds-iis-migration*на source, очиститьC:\ProgramData\ssh\administrators_authorized_keysна RUVDS.
Полный план + Completed + Open questions + Remaining steps — в iis-migration-to-ruvds.md. Branch: master
Branch: master
⚪ [infra-inventory] — two-tier инвентаризация: public-карта в global wiki + admin-detailed runbook локально
Status: ready
Where I stopped: (not started — создана 2026-05-22 из инцидента gitea. vs git. + перепутанный source/dest IP в traefik access-логах; scope расширена в тот же день — single-page → two-tier per user «у все общее представление, у админа полное»)
Next action: см. полный план в infra-inventory.md. Шаги: (1) probing-фаза одна для обоих — nslookup известных subdomain'ов + vds-ops/synology-ops ops_docker_ps/inspect + knowledge_search по существующим bootstrap-concept'ам + rg "kzntsv.site" по ~/projects/. (2) Write A — light public в projects-wiki/concepts/infrastructure-inventory.md (машины, canonical hostnames, anti-aliases) → knowledge_ingest. (3) Write B — heavy admin в .admin/.wiki/concepts/infrastructure-stack.md (per-stack: версии, internal IPs, volumes, depends-on, backup paths, DR pointers) → commit + push. (4) Cross-refs A↔B + pointer в .admin/.wiki/CLAUDE.md Domain conventions.
Branch: n/a
⚪ [windows-host-fallback-backup-daily] — daily backup windows-host → kreknin, держим warm-standby готовым принять traffic при VDS/RUVDS failure
Status: ready
Where I stopped: (not started — re-scoped 2026-05-24 из cms-stopgap-backup-daily после migration MSSQL+sites)
Why: primary backup'ы покрыты ruvds-backup-daily-kreknin 🟢 (sites + IIS configs + certs) + vds-backup-rsync-kreknin 🟢 (MSSQL/MinIO/VDS stacks). Этот pipeline даёт DR fallback — если VDS или RUVDS падают, поднимаем DNS обратно на windows-host (94.19.247.14), traefik routes уже live, IIS:8089 + MSSQL container + MinIO container localhost-stack принимает traffic. Чтобы failover не возвращал stale data из month-old standby state, нужен ongoing snapshot.
Also blocks image-pipeline DR: CMS image rendering хардкодит imgproxy.kzntsv.site через DLL (см. [iis-cutover-to-vds-services] MinIO caveat). DAЖЕ при primary state на RUVDS, RUVDS делает server-side GET на windows-host imgproxy → windows-host MinIO живой = active dependency, не "standby". Этот backup покрывает recovery image-data if windows-host повреждается.
Next action: см. windows-host-fallback-backup-daily.md §Scope. Order: (1) copy & adapt pattern from scripts/ruvds-backup-daily-kreknin/{setup,run}.ps1, (2) docker inspect MinIO для data dir path, (3) MSSQL BACKUP DATABASE x5 DBs (MoreThenCms + Stayer* + stostayer + TireService), (4) rclone sync 5 components → kreknin:NetBackup/windows-host/<date>/, (5) ScheduledTask WindowsHost-Backup-Daily daily 03:00 MSK (раньше RUVDS 04:30 + VDS 05:00 — sequential snapshots на kreknin), (6) ntfy vds-backup + email через Yandex SMTP (re-use creds из pass show snolla-smtp/full-env), (7) smoke recovery test (restore .bak в чистый MSSQL container, SELECT works).
Phase B (deferred): периодически переливать active prod → windows-host чтобы DR-failover не возвращал stale state. Через 1-2 недели после Phase A — посмотрим насколько diverged.
Branch: master
🔵 [books-vds-bookva-bootstrap] — Ops-таска для Фазы 4 дизайна tenant-split из victor/books (см. mcp__projects-meta__knowledge_get slug=concepts/tenant-split). Поднять новый VDS для Bookva — billing на юрлицо Bookva (учредители развелись, каждое юрлицо платит инфру напрямую провайдеру).
Контекст dev-source: дизайн в victor/books .wiki/concepts/tenant-split.md; brainstorm trace ~/projects/.workshop/.archive/2026-05-24-books-tenant-split.md.
Direction: Slovo остаётся на текущем VDS, Bookva переезжает на новый.
Acceptance:
- Новый VDS у провайдера (Rusonyx или другой по предпочтению Bookva), billing-account оформлен на юрлицо Bookva.
- Docker + traefik + certbot развёрнуты.
- DNS
*.bookva.<tld>готов резолвиться на новый IP (фактический switch — вbooks-dns-cutover-bookva). - SSH-ключи: только инженерные (core-разраб + админ Bookva, если есть). Аналитики Bookva — НЕ имеют SSH к новому VDS.
Status: blocked
Where I stopped: (not started)
Next action: Pre-step: прочитать concepts/tenant-split.md § «Фаза 4» в victor/books (через mcp__projects-meta__knowledge_get slug=concepts/tenant-split или git clone victor/books → .wiki/concepts/tenant-split.md).
- Согласовать с учредителем Bookva: provider, configuration (CPU/RAM/disk), регистрация billing'а на юрлицо Bookva.
- Provision VDS, базовая настройка (firewall, fail2ban, SSH ключи).
- Установить Docker + docker-compose.
- Развернуть traefik + certbot из overlay-репо
victor/books-bookva/deploy/traefik.compose.yml. - Подготовить DNS-зону
bookva.<tld>(создать A-records, TTL=300 для возможности быстрого switch'а). - Smoke:
curl https://placeholder.bookva.<tld>→ 200 от nginx-placeholder или из traefik. - Документировать в
victor/books-bookva/README.md: hostname, IP, как ssh, runbook smoke-теста. - Закрыть с note: «VDS поднят, IP=<...>, готов к stack deploy».
Blocker: victor/books
tenant-split-pointers+overlay-repos-bootstrap-bookva-slovo+compose-second-mariadb-instance+per-tenant-backup-and-observability(стек уже работает на текущем VDS логически — пора готовить физический переезд). Branch: n/a
🔵 [books-dns-cutover-bookva] — Ops-таска для Фазы 4, шаг 5 дизайна tenant-split из victor/books. DNS switch *.bookva.<tld> → новый VDS IP, с parallel-run старого bookva-стека на shared VDS 7 дней без публичного hostname.
Контекст dev-source: дизайн в victor/books .wiki/concepts/tenant-split.md § «Фаза 4».
Acceptance:
- DNS
*.bookva.<tld>(или конкретный hostname Bookva — определяется учредителем) указывает на новый VDS IP. - Старый bookva-стек на shared VDS остаётся запущенным, без публичного hostname (traefik labels убраны или disabled), доступен только по docker-сети для возможного отката.
- Smoke с двух разных сетей (mobile + офисный wifi) —
https://<bookva-hostname>отвечает с нового VDS. - Per-VDS backup'ы на новом VDS подтверждены — есть snapshot спустя 24ч после DNS-switch'а.
- Через 7 дней parallel-run без откатов — decommission старого bookva-стека (см. Фаза 4, шаг 7 в spec).
Status: blocked
Where I stopped: (not started)
Next action: Pre-step: прочитать concepts/tenant-split.md § «Фаза 4, шаги 4–7» в victor/books.
- Maintenance window 1–2ч (объявить за 7 дней).
- Финальная синхронизация:
mysqldump mariadb-bookvaна текущем VDS →mysqlна новом VDS (если schema/data разошлись с момента Фазы 2). - Smoke на новом VDS до DNS-switch'а: hosts-файл override → проверить login + base flow.
- DNS-switch: меняем A-record(s) для bookva-hostname на new IP. TTL=300 уже стоял (Phase 4 step 1).
- Через 1ч (TTL expiry + propagation): smoke с двух сетей.
- На старом VDS — отключить traefik labels для bookva-стека (контейнеры продолжают работать, но не доступны снаружи).
- Parallel-run 7 дней. Каждый день — smoke. Per-VDS backup на новом VDS — проверить хотя бы 1 успешный snapshot.
- Если за 7 дней проблем нет → закрыть с note «cutover stable». Если есть — DNS rollback на старый IP, follow-up debug task в victor/books.
- Decommission старого bookva-стека на shared VDS (отдельный шаг, не в этой таске — финальный backup в архив +
docker compose down+ volume drop). Blocker:books-vds-bookva-bootstrap+ victor/bookspwa-redirect-handoff(SW bump выкачен в shared API за 1–2 недели до этой таски). Branch: n/a
⚪ [books-ssh-audit-shared-vds] — Ops-таска для Фазы 3, шаг 2 дизайна tenant-split из victor/books. SSH-аудит на текущем shared VDS перед cutover'ом. На промежуточной стадии (1 VDS, 2 стека, 2 БД) — infra-level изоляция временно скомпрометирована: пользователь с SSH к VDS может прочитать БД соседнего tenant'а через localhost. Минимизировать риск до Фазы 3.
Контекст dev-source: дизайн в victor/books .wiki/concepts/tenant-split.md § «Двухуровневая изоляция пользователей → Infra-level».
Не блокируется ничем — можно сделать сразу при начале Фазы 2 logical split.
Acceptance:
~/.ssh/authorized_keysна shared VDS reviewed.- Все ключи, не принадлежащие core-разрабу или формально-назначенному админу клиента — отозваны.
- Особое внимание: ключи аналитиков (если они когда-то выдавались) — отозвать. Аналитики работают через app-level login, не SSH.
- Документировать список оставшихся ключей в
OpeItcLoc03/admin/.wiki/concepts/books-ssh-access.md(или эквивалент): owner, дата выдачи, обоснование.
Status: ready
Where I stopped: (not started)
Next action: 1. ssh user@<shared-vds> 'cat ~/.ssh/authorized_keys' или через panel провайдера.
2. Для каждого ключа: идентифицировать owner (по комментарию в ключе, по дате последнего login через last, по записи в локальной памяти).
3. Сформировать список «оставить / отозвать»:
- Оставить: core-разраб (ты), формально-назначенный админ клиента (если есть).
- Отозвать: аналитики, бывшие сотрудники, неопознанные ключи.
- Согласовать с учредителями (формально) перед удалением — особенно если есть ключи их подчинённых.
- Удалить отозванные ключи из
authorized_keys. Backup старого файла в/etc/ssh/authorized_keys.pre-audit-$(date +%F). - Verify:
ssh -i <revoked-key> user@hostотвергается. - Документировать в
OpeItcLoc03/admin/.wiki/concepts/books-ssh-access.md. - Закрыть с note: «N ключей оставлено (), M отозвано». Branch: n/a