Реализован production-hardening по fix1: env/reconfigure, IPv4-only, TLS, secrets, firewall, docs
This commit is contained in:
@@ -0,0 +1,705 @@
|
||||
Ты работаешь с проектом 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.
|
||||
Reference in New Issue
Block a user