Ты работаешь с проектом HY2XS_flamy / HY2XS.

Контекст проекта:
HY2XS — это production installer/orchestrator для установки Hysteria2 + встроенной HY2XS admin panel на Debian 12 VPS. Оркестратор написан на Bun + TypeScript, admin panel является fork/refactor h-ui и собирается заранее, на target-сервере сборки быть не должно. Hysteria2 должен оставаться upstream vanilla binary. Проект не должен превращаться в Telegram-бота, CRM или generic server manager. Это узкий installer/runtime manager для Hysteria2 + HY2XS admin.

Главная задача:
Провести production-hardening pass без костылей и без legacy. Исправить код, шаблоны, systemd, firewall, env/config layer, документацию и acceptance checks так, чтобы проект соответствовал официальным подходам Hysteria2/systemd и собственным docs проекта.

ВАЖНО:
- Не делай косметические правки вместо архитектурных.
- Не добавляй временные обходы.
- Не оставляй legacy h-ui функциональность, если она не входит в scope HY2XS.
- Не меняй архитектуру на “собирать на target-сервере”.
- Не форкай Hysteria2.
- Не делай IPv6 support. В этом проекте серверы только IPv4. IPv6 должен быть явно out of scope.
- Все bind/listen должны быть IPv4-only.
- Все секреты должны быть chmod 600/root-only или доступны только нужному сервисному пользователю.
- После правок обнови документацию, примеры и acceptance criteria.

Перед правками:
1. Изучи текущую структуру проекта:
   - README.md
   - docs/*.md
   - hy2xs_implementation_plan-no_git/*.txt
   - orchestrator/src/**
   - package/templates/**
   - package/systemd/**
   - package/examples/**
   - apps/**
   - apps/frontend/**
   - tools/build/**
2. Сверь спорные места с официальными docs:
   - Hysteria2 server config
   - Hysteria2 ACME/TLS
   - Hysteria2 HTTP auth
   - Hysteria2 trafficStats API
   - Hysteria2 install script behavior
   - systemd hardening options
   - nftables safe apply practices
   - Bun standalone compile behavior
3. Найди рассинхроны между docs и реализацией.
4. Исправь реализацию под production, а не просто подгони docs под текущий код.

Ключевые проблемы, которые нужно исправить:

1. Реализовать нормальный env/config layer

Сейчас /etc/hysteria/post-install.env существует как reference-файл, но фактически не является полноценным слоем конфигурации.

Нужно:
- Ввести единый runtime/deploy env-файл, который оркестратор умеет читать, валидировать и применять.
- Рекомендуемый путь:
  - /etc/hy2xs/hy2xs.env как основной editable config layer
  - /etc/hysteria/post-install.env как generated deployment snapshot/reference
  Либо можно оставить один /etc/hysteria/post-install.env, но только если он реально становится читаемым оркестратором config layer. Предпочтительно разделить editable config и generated snapshot.
- Файл должен иметь права 0600.
- Файл должен содержать основные production-параметры:
  - HY2XS_DOMAIN
  - HY2XS_PUBLIC_HOST
  - HY2XS_PUBLIC_PORT
  - HY2XS_IPV6_ENABLED=false
  - HY2XS_SSH_PORT
  - HY2XS_FIREWALL_ENABLED
  - HY2XS_FIREWALL_STAGED_APPLY
  - HY2XS_UI_BIND_HOST=127.0.0.1
  - HY2XS_UI_PORT
  - HY2XS_ADMIN_USER
  - HY2XS_ADMIN_INITIAL_PASSWORD или путь к bootstrap secret file
  - HY2XS_FORCE_PASSWORD_CHANGE=true
  - HY2XS_TLS_MODE=acme|file|self_signed_dev
  - HY2XS_ACME_EMAIL
  - HY2XS_TLS_CERT_PATH
  - HY2XS_TLS_KEY_PATH
  - HY2XS_HYSTERIA_BIND_HOST=0.0.0.0
  - HY2XS_HYSTERIA_PORT=443
  - HY2XS_HYSTERIA_AUTH_MODE=http
  - HY2XS_HYSTERIA_AUTH_URL=http://127.0.0.1:<ui_port>/hui/hysteria2/auth
  - HY2XS_HYSTERIA_TRAFFIC_STATS_HOST=127.0.0.1
  - HY2XS_HYSTERIA_TRAFFIC_STATS_PORT
  - HY2XS_HYSTERIA_TRAFFIC_STATS_SECRET
  - HY2XS_HYSTERIA_OBFS_TYPE=salamander
  - HY2XS_HYSTERIA_OBFS_PASSWORD
  - HY2XS_HYSTERIA_BANDWIDTH_UP
  - HY2XS_HYSTERIA_BANDWIDTH_DOWN
  - HY2XS_HYSTERIA_IGNORE_CLIENT_BANDWIDTH=false
  - HY2XS_HYSTERIA_CONFIG_PATH=/etc/hysteria/config.yaml
  - HY2XS_HYSTERIA_VERSION or latest policy
  - HY2XS_INSTALL_DIR=/opt/hy2xs-admin
  - HY2XS_DATA_DIR=/var/lib/hy2xs-admin
  - HY2XS_LOG_DIR=/var/log/hy2xs
- Добавить в orchestrator:
  - загрузку env-файла;
  - строгую валидацию;
  - нормализацию типов;
  - запрет несовместимых комбинаций;
  - dry-run вывод;
  - явную команду reconfigure.
- Изменение env-файла не должно автоматически менять runtime.
- Применение только через явную команду:
  - hy2xs-orchestrator install --config /path/to/hy2xs.env
  - hy2xs-orchestrator reconfigure --config /etc/hy2xs/hy2xs.env --dry-run
  - hy2xs-orchestrator reconfigure --config /etc/hy2xs/hy2xs.env --apply
- Если reconfigure меняет port/listen/firewall/TLS, он должен:
  - валидировать новый config;
  - сделать backup текущих config/unit/firewall;
  - применить staged;
  - выполнить smoke-check;
  - откатить изменения при провале.

Файлы для правок:
- orchestrator/src/cli.ts
- orchestrator/src/types/context.ts
- orchestrator/src/commands/install.ts
- добавить orchestrator/src/commands/reconfigure.ts
- добавить orchestrator/src/config/env.ts или похожий модуль
- orchestrator/src/steps/env.ts
- package/templates/env/*
- package/examples/*
- docs/09-post-install-env.md
- docs/08-orchestrator-spec.md
- docs/11-testing-and-acceptance.md

2. Зафиксировать IPv4-only модель

Требование:
Проект работает только с IPv4. IPv6 не нужен и не должен случайно включаться.

Нужно:
- В Hysteria config не использовать listen вида :443.
- Использовать только:
  listen: 0.0.0.0:<port>
- HY2XS admin должен слушать только IPv4 bind host:
  127.0.0.1:<ui_port> по умолчанию.
- Не использовать [::], ::, dual-stack listen.
- В docs явно указать:
  - IPv6 unsupported/out of scope;
  - все публичные входящие соединения идут через IPv4;
  - домен должен иметь A-record;
  - AAAA-record не используется и не требуется;
  - если у домена есть AAAA, оператор должен понимать, что HY2XS его не обслуживает.
- В preflight добавить проверку:
  - домен резолвится в IPv4 A-record;
  - если есть AAAA, вывести warning, но не включать IPv6;
  - public_host/client URL строится только по IPv4-домену/IPv4 endpoint.
- В firewall использовать IPv4-only nftables rules. Не использовать inet table как способ “случайно покрыть IPv6”, если проект IPv4-only.
- Если на сервере IPv6 включен, HY2XS всё равно не должен слушать IPv6.

Файлы:
- package/templates/hysteria/config.yaml.tpl
- package/templates/nftables/hy2xs.nft.tpl
- orchestrator/src/steps/preflight.ts
- orchestrator/src/steps/config.ts
- orchestrator/src/steps/firewall.ts
- docs/03-server-hysteria2.md
- docs/05-client-and-access-scope.md
- docs/07-systemd-and-firewall.md
- docs/12-operations-and-troubleshooting.md

3. Исправить Hysteria2 listen/public endpoint split

Сейчас есть риск, что client URL строится из listen, что неверно.

Нужно разделить:
- bind_host: 0.0.0.0
- bind_port: 443
- public_host: domain or IPv4
- public_port: 443

Hysteria server config использует bind_host/bind_port.
Client URL/subscription использует public_host/public_port.

Нельзя строить client URL из поля listen.
Нельзя использовать 0.0.0.0 в client URL.

Проверь и исправь:
- apps/service/hysteria2_api.go
- apps/model/bo/hysteria2.go
- apps/model/bo/hysteria2_api.go
- apps/model/dto/hysteria2.go
- apps/model/vo/hysteria2.go
- все места, где public URL строится через Listen.
- package/templates/hysteria/config.yaml.tpl
- docs.

Acceptance:
- При listen: 0.0.0.0:443 клиентский URL должен быть hysteria2://password@example.com:443/...
- В URL не должно быть 0.0.0.0.
- При public_port=443 порт можно явно оставить или нормализовать по принятому формату, но поведение должно быть стабильным и протестированным.

4. Исправить TLS/ACME flow

Сейчас self-signed сертификат фактически используется как default. Это не production-ready.

Нужно:
- Добавить TLS modes:
  - acme — production default
  - file — production для собственного cert/key
  - self_signed_dev — только dev/lab, запрещён для non-interactive production без явного флага
- В production default использовать ACME, если задан domain и acme_email.
- Для acme mode Hysteria config должен использовать acme block, а не tls cert/key.
- Для file mode использовать tls.cert/tls.key.
- Для self_signed_dev:
  - явно генерировать self-signed cert;
  - явно маркировать install как dev/lab;
  - client config должен включать insecure только для этого режима.
- Не смешивать acme и tls file в одном config.
- Добавить в env:
  - HY2XS_TLS_MODE
  - HY2XS_ACME_EMAIL
  - HY2XS_TLS_CERT_PATH
  - HY2XS_TLS_KEY_PATH
- Проверить, что generated config соответствует официальной схеме Hysteria2.

Файлы:
- orchestrator/src/steps/config.ts
- package/templates/hysteria/config.yaml.tpl
- package/templates/env/*
- docs/03-server-hysteria2.md
- docs/05-client-and-access-scope.md
- docs/11-testing-and-acceptance.md

Acceptance:
- acme mode генерирует только acme block.
- file mode генерирует только tls cert/key block.
- self_signed_dev генерирует tls cert/key + client insecure.
- production install без domain/acme_email должен завершиться ошибкой или потребовать явный self_signed_dev.

5. Исправить TrafficStats API secret

Сейчас Hysteria config получает HYSTERIA_API_SECRET, но HY2XS admin использует JWT_SECRET для trafficStats API. Это неверно.

Нужно:
- Ввести отдельную настройку:
  HY2XS_HYSTERIA_TRAFFIC_STATS_SECRET
- Один и тот же secret должен использоваться:
  - в Hysteria config:
    trafficStats.secret
  - в HY2XS admin при вызовах:
    /traffic
    /online
    kick user / disconnect if exists
- Не использовать JWT_SECRET для Hysteria API.
- JWT_SECRET должен отвечать только за авторизацию HY2XS admin.
- Добавить smoke-check:
  - запрос к trafficStats API с правильным secret проходит;
  - запрос с неправильным secret не проходит.
- Обновить docs.

Файлы:
- apps/service/hysteria2_api.go
- apps/proxy/hysteria2_api.go
- apps/model/constant/config.go
- apps/service/config.go
- orchestrator/src/steps/config.ts
- package/templates/hysteria/config.yaml.tpl
- package/templates/env/*
- docs/03-server-hysteria2.md
- docs/04-admin-panel-h-ui-fork.md
- docs/11-testing-and-acceptance.md

6. Убрать default admin sysadmin/sysadmin

Сейчас seed создаёт admin sysadmin/sysadmin. Это production blocker.

Нужно:
- Убрать дефолтный predictable admin password.
- Во время install генерировать bootstrap admin password.
- Записывать его в root-only файл:
  /etc/hy2xs/bootstrap-admin.secret
  chmod 600
- Или выводить один раз в конце установки + сохранять в защищённый файл.
- Admin username должен задаваться через env:
  HY2XS_ADMIN_USER
- При первом логине требовать смену пароля:
  HY2XS_FORCE_PASSWORD_CHANGE=true
- Не использовать con_pass = admin password.
- con_pass для Hysteria user должен быть отдельным случайным secret.
- Перейти с SHA224 на нормальный password hashing:
  - bcrypt или argon2id.
- Сделать backward-compatible migration:
  - старые SHA224 пароли распознавать;
  - после успешного login перехешировать в новый формат;
  - новые пароли сохранять только в новом формате.
- Обновить docs.

Файлы:
- apps/dao/sqlite.go
- apps/util/encrypt.go
- apps/service/account.go
- apps/model/entity/account.go
- apps/model/dto/account.go
- apps/controller/account.go
- orchestrator/src/commands/install.ts
- orchestrator/src/steps/env.ts
- package/templates/env/*
- docs/04-admin-panel-h-ui-fork.md
- docs/09-post-install-env.md
- docs/11-testing-and-acceptance.md

Acceptance:
- После fresh install нет sysadmin/sysadmin.
- Login невозможен старым дефолтным паролем.
- Bootstrap password уникален для каждой установки.
- Password hash не является быстрым SHA digest.
- force password change работает.

7. Исправить UI bind host

Сейчас CLI имеет --ui-bind-host, systemd передаёт HY2XS_UI_BIND_HOST, но Go server фактически слушает :port на всех интерфейсах.

Нужно:
- Go server должен читать HY2XS_UI_BIND_HOST.
- Default: 127.0.0.1.
- Addr должен быть:
  127.0.0.1:<port>
  или другой явно заданный IPv4.
- Запретить пустой host как bind all.
- Запретить :: и IPv6 bind.
- Если оператор явно задаёт 0.0.0.0, требовать warning/explicit flag, либо запретить в production.
- systemd unit должен передавать HY2XS_UI_BIND_HOST.
- smoke-check должен проверять, что UI не слушает 0.0.0.0, если bind host 127.0.0.1.

Файлы:
- apps/cmd/server.go
- apps/service/server.go
- package/systemd/hy2xs-admin.service
- orchestrator/src/steps/systemd.ts
- orchestrator/src/steps/smoke.ts
- docs/04-admin-panel-h-ui-fork.md
- docs/07-systemd-and-firewall.md

Acceptance:
- ss -ltnp показывает 127.0.0.1:<ui_port>, а не 0.0.0.0:<ui_port>.
- UI недоступен с внешнего интерфейса без reverse proxy/tunnel.
- --ui-bind-host реально влияет на bind.

8. Запускать HY2XS admin не от root

Сейчас systemd unit не задаёт User/Group, значит admin работает от root.

Нужно:
- Создать системного пользователя:
  hy2xs-admin
- Запускать HY2XS admin от User=hy2xs-admin Group=hy2xs-admin.
- Настроить директории:
  - /opt/hy2xs-admin read-only для binary/assets
  - /var/lib/hy2xs-admin writable data
  - /var/log/hy2xs writable logs
- В systemd добавить hardening:
  - NoNewPrivileges=true
  - PrivateTmp=true
  - ProtectHome=true
  - ProtectSystem=strict
  - ReadWritePaths=/var/lib/hy2xs-admin /var/log/hy2xs
  - RestrictAddressFamilies=AF_INET AF_UNIX
  - CapabilityBoundingSet= empty where possible
  - AmbientCapabilities= empty where possible
- Если UI должен перезапускать Hysteria или читать privileged files, не запускать весь UI от root.
  Вместо этого:
  - либо убрать такие операции из UI;
  - либо сделать отдельный узкий root helper;
  - либо использовать строго ограниченный sudoers/polkit rule.
- Не оставлять широкие root-права.

Файлы:
- package/systemd/hy2xs-admin.service
- orchestrator/src/steps/filesystem.ts
- orchestrator/src/steps/systemd.ts
- apps/proxy/process.go
- apps/service/hysteria2.go
- apps/service/config.go
- docs/04-admin-panel-h-ui-fork.md
- docs/07-systemd-and-firewall.md

Acceptance:
- systemctl show hy2xs-admin показывает User=hy2xs-admin.
- Процесс не root.
- UI продолжает работать.
- Нет записи в /etc/hysteria/config.yaml от имени неподходящего процесса без контролируемого helper/reconfigure.

9. Исправить права /etc/hysteria/config.yaml

Сейчас orchestrator пишет config chmod 0600, но UI может перезаписать его chmod 0644.

Нужно:
- Всегда писать /etc/hysteria/config.yaml с правами 0600.
- owner должен быть корректным для Hysteria service.
- Если UI больше не должен напрямую писать config, убрать такую возможность или перенести в orchestrator reconfigure.
- Писать config atomic:
  - temporary file
  - fsync if needed
  - chmod/chown
  - rename
  - validate
  - restart/reload
- Не допускать world-readable secrets.

Файлы:
- orchestrator/src/steps/config.ts
- apps/service/hysteria2.go
- apps/service/config.go
- docs/03-server-hysteria2.md
- docs/07-systemd-and-firewall.md

Acceptance:
- stat -c "%a %U %G" /etc/hysteria/config.yaml показывает 600 и ожидаемого owner/group.
- В config есть secrets, но файл не world-readable.
- UI не ослабляет права после сохранения.

10. Переделать firewall apply на безопасный staged mode

Сейчас firewall может резко применить policy drop и отрезать SSH.

Нужно:
- Не перезаписывать слепо весь /etc/nftables.conf без staged rollback.
- Использовать include-файл, например:
  /etc/nftables.d/hy2xs.nft
- Перед apply выполнять:
  nft -c -f <candidate>
- Сделать staged apply:
  - backup current rules/config
  - install rollback timer через systemd-run или эквивалент
  - apply candidate
  - проверить SSH port rule
  - проверить Hysteria UDP port
  - проверить UI local bind
  - если checks passed — cancel rollback
  - если failed — rollback
- IPv4-only:
  - table ip hy2xs
  - не использовать IPv6 rules как supported path.
- Allow:
  - lo
  - established/related
  - SSH TCP port from IPv4
  - Hysteria UDP port from IPv4
  - optionally ICMP
  - UI TCP только с 127.0.0.1
- Default drop только после staged safety.
- Если --skip-firewall, не открывать UI публично.

Файлы:
- orchestrator/src/steps/firewall.ts
- package/templates/nftables/hy2xs.nft.tpl
- docs/07-systemd-and-firewall.md
- docs/11-testing-and-acceptance.md

Acceptance:
- nft -c проходит.
- Неправильный SSH port не применяет irreversible lockout.
- UI не доступен с внешнего интерфейса.
- Hysteria UDP port открыт.
- IPv6 не считается поддерживаемым.

11. Удалить port hopping legacy

Docs говорят no port hopping, но code всё ещё инициализирует:
- service.InitTableAndChain()
- service.InitPortHopping()

Нужно:
- Убрать port hopping из production path.
- Удалить или отключить:
  - apps/service/forward.go
  - связанные nft/iptables вызовы
  - связанные routes/UI элементы
  - связанные config fields
- Если удалить полностью нельзя за один pass, закрыть build tag’ом или runtime flag default false, но production binary не должен инициализировать port hopping.
- Не создавать nft table/chain при старте HY2XS admin.
- Обновить docs.

Файлы:
- apps/cmd/server.go
- apps/service/forward.go
- apps/router/*
- apps/frontend/src/views/*
- docs/04-admin-panel-h-ui-fork.md
- docs/10-access-layer-out-of-scope.md

Acceptance:
- grep по InitPortHopping не показывает production вызов.
- При старте UI не создаёт nft/iptables rules.
- В UI нет port hopping управления.

12. Убрать legacy updater/GitHub logic из UI

HY2XS admin не должен быть updater’ом h-ui/original repo.

Нужно:
- Найти и удалить legacy code, связанный с:
  - original h-ui repo
  - GitHub releases
  - self-update UI
  - update checker
  - install/update Hysteria из UI, если это зона orchestrator
- В Go dependency audit:
  - github.com/google/go-github/v39 сейчас используется только apps/util/github.go.
  - Если self-update/GitHub release logic удаляется, удалить util/github.go и go-github из go.mod/go.sum.
- Не оставлять неиспользуемые функции “на потом”.

Файлы:
- apps/util/github.go
- apps/go.mod
- apps/go.sum
- apps/controller/config.go
- apps/service/config.go
- frontend config/settings views
- docs/04-admin-panel-h-ui-fork.md
- docs/10-access-layer-out-of-scope.md

Acceptance:
- go mod tidy удаляет google/go-github, если больше не нужен.
- UI не показывает updater legacy.
- Docs говорят, что update/upgrade — зона orchestrator/package, не admin panel.

13. Проверить и почистить frontend dependencies

В apps/frontend/package.json есть вероятные рудименты.

Проверь фактическое использование и удали неиспользуемое:
- echarts — в текущем коде не найдено использование.
- screenfull — в текущем коде не найдено использование.
- path-to-regexp — в текущем коде не найдено использование.
- fast-glob — в vite.config.ts не используется.
- @types/path-browserify — нужен только если path-browserify остаётся.
- vite-plugin-dynamic-base — используется в vite.config.ts, но проверить, нужен ли HY2XS dynamic base. Если UI всегда от root path, убрать.
- unocss — используется в vite config, но проверить, реально ли есть UnoCSS classes. Если нет — убрать.
- unplugin-icons / @iconify-json/ep — оставить только если реально нужны auto icons.
- vuedraggable — используется в ImputMultiple, оставить если компонент нужен.
- path-browserify — используется в Sidebar/TagsView, оставить или заменить на простую path join utility без browser polyfill.
- @vueuse/core — используется, оставить или заменить точечно, если хочется уменьшить bundle.
- nprogress — используется, оставить.
- copy-to-clipboard — используется, оставить или заменить navigator.clipboard, если поддержка позволяет.

После удаления:
- обновить pnpm-lock.yaml;
- убедиться, что frontend build проходит;
- удалить сгенерированные auto-import/component d.ts, если они не должны быть в repo, либо обновить их корректно;
- не оставлять импортов на удалённые пакеты.

Файлы:
- apps/frontend/package.json
- apps/frontend/pnpm-lock.yaml
- apps/frontend/vite.config.ts
- apps/frontend/src/**
- docs/04-admin-panel-h-ui-fork.md

Acceptance:
- pnpm install --frozen-lockfile проходит.
- pnpm build:prod проходит.
- grep не находит удалённые пакеты в src/vite config.
- UI работает без legacy dependencies.

14. Исправить Hysteria install flow

Сейчас installer использует official script через curl/sh и не pin’ит версию.

Нужно:
- Добавить возможность pin версии:
  HY2XS_HYSTERIA_VERSION=vX.Y.Z или latest.
- Если latest — явно записать фактически установленную версию в post-install snapshot.
- Использовать official installer корректно.
- Если используется curl | bash/script, сделать безопаснее:
  - скачать script в temp file;
  - проверить download success;
  - по возможности checksum/signature/version;
  - запускать bash, если official docs требуют bash.
- После установки проверить:
  - binary exists;
  - hysteria version;
  - expected service conflict отсутствует или осознанно заменён.
- Если official installer создаёт свой service, HY2XS должен явно документировать и контролировать replacement.

Файлы:
- orchestrator/src/steps/hysteria.ts
- orchestrator/src/steps/smoke.ts
- docs/02-build-layer-and-package.md
- docs/03-server-hysteria2.md
- docs/08-orchestrator-spec.md

15. Улучшить smoke/acceptance checks

Текущий smoke слишком слабый.

Добавить проверки:
- systemd units active:
  - hysteria-server
  - hy2xs-admin
- Hysteria UDP port слушает IPv4.
- UI слушает только expected IPv4 bind host.
- UI не слушает 0.0.0.0 при bind 127.0.0.1.
- Auth endpoint отвечает корректно:
  - /hui/hysteria2/auth для тестового/существующего пользователя.
- TrafficStats API:
  - correct secret works;
  - wrong secret denied.
- Hysteria config syntactically valid.
- TLS mode соответствует env:
  - acme mode содержит acme и не содержит tls cert/key.
  - file mode содержит tls cert/key и не содержит acme.
  - self_signed_dev clearly marked.
- Firewall rules installed and nft -c passes.
- File permissions:
  - /etc/hy2xs/hy2xs.env 0600
  - /etc/hysteria/post-install.env 0600
  - /etc/hysteria/config.yaml 0600
  - bootstrap-admin.secret 0600
- No default sysadmin/sysadmin.
- No IPv6 listen:
  - ss output must not show [::] for HY2XS/Hysteria.
- No port hopping init.
- Reboot persistence documented or testable.

Файлы:
- orchestrator/src/steps/smoke.ts
- docs/11-testing-and-acceptance.md
- package/install.sh

16. Обновить docs и убрать рассинхрон

Обновить:
- README.md
- docs/01-architecture-baseline.md
- docs/02-build-layer-and-package.md
- docs/03-server-hysteria2.md
- docs/04-admin-panel-h-ui-fork.md
- docs/05-client-and-access-scope.md
- docs/06-speed-limits-and-congestion.md
- docs/07-systemd-and-firewall.md
- docs/08-orchestrator-spec.md
- docs/09-post-install-env.md
- docs/10-access-layer-out-of-scope.md
- docs/11-testing-and-acceptance.md
- docs/12-operations-and-troubleshooting.md
- hy2xs_implementation_plan-no_git/*.txt если они остаются как актуальные документы.

Docs должны фиксировать:
- HY2XS = Bun/TypeScript orchestrator + bundled HY2XS admin + upstream Hysteria2.
- No Telegram bot.
- No port hopping.
- No target-side build.
- No IPv6 support.
- IPv4-only bind/listen.
- Production TLS default = ACME.
- self-signed only dev/lab.
- env/config layer and reconfigure flow.
- admin panel не updater и не generic server manager.
- admin panel не работает от root.
- firewall staged apply.
- secret/file permission policy.
- acceptance checks.

Также исправить README:
- Убедиться, что build command указывает реальный путь.
- Если фактический build script tools/build/build.sh, README не должен ссылаться на builder/build.sh.
- Все команды должны соответствовать текущей структуре.

17. Общие требования к качеству

После правок выполнить:
- gofmt по Go-коду.
- go mod tidy.
- frontend lockfile update.
- TypeScript check для orchestrator.
- Build orchestrator.
- Build frontend.
- Build Go admin.
- Smoke если возможно в среде.
- grep-проверки:
  - нет sysadmin/sysadmin как production seed.
  - нет InitPortHopping production вызова.
  - нет listen: :{{HYSTERIA_PORT}}.
  - нет UI bind ":8080" без host.
  - нет JWT_SECRET как Hysteria trafficStats secret.
  - нет chmod 0644 для /etc/hysteria/config.yaml.
  - нет IPv6 listen [::] / "::" в runtime defaults.
  - нет h-ui legacy updater/original repo references, если они вне scope.

Не делай:
- Не оставляй TODO вместо исправления P0.
- Не добавляй reverse proxy как обязательную часть.
- Не добавляй Docker requirement.
- Не добавляй Telegram/bot features.
- Не добавляй IPv6.
- Не оставляй root admin panel.
- Не делай “если не получилось, chmod 777”.
- Не ослабляй firewall ради прохождения smoke.
- Не используй JWT_SECRET для Hysteria API.
- Не используй 0.0.0.0 в client URL.
- Не делай self-signed production default.

Ожидаемый результат:
1. Полный diff с исправлением production blockers.
2. Обновлённые docs.
3. Обновлённые templates/examples.
4. Удалённые legacy dependencies/code.
5. Понятный reconfigure/env flow.
6. IPv4-only модель зафиксирована в коде и docs.
7. Расширенные smoke/acceptance checks.
8. Краткий отчёт:
   - что исправлено;
   - какие файлы изменены;
   - какие legacy части удалены;
   - какие команды проверки запускались;
   - что осталось как tech debt, если что-то невозможно закрыть за один pass.