183 lines
No EOL
15 KiB
Markdown
183 lines
No EOL
15 KiB
Markdown
# Задание A50: аккаунты, обнаружение моделей и состояние проверки
|
||
|
||
## Дата поступления
|
||
2026-08-31
|
||
|
||
## База
|
||
|
||
`origin/main` (`17b368a`).
|
||
|
||
```
|
||
git fetch origin --prune
|
||
git checkout -b antigravity/a50-accounts-discovery origin/main
|
||
```
|
||
|
||
В `main` напрямую не пушить.
|
||
|
||
## Порядок исполнения
|
||
|
||
Два прохода: **Flash** реализует, **Pro** проводит аудит. Пункт **P0-8** написан для аудитора.
|
||
|
||
Зона: Python-часть провайдеров и экран «Аккаунты». С A49 (субагенты, скиллы, память) не пересекается.
|
||
|
||
---
|
||
|
||
## Задача
|
||
|
||
Восемь замечаний владельца после установки сборки `17b368a`. Причины найдены и проверены ревьюером исполнением — заново не выяснять.
|
||
|
||
---
|
||
|
||
## P0-1. Аккаунт сохраняется в чужой слот и рапортует об успехе
|
||
|
||
Самое серьёзное. Проверено вызовом:
|
||
|
||
```
|
||
add_account provider=nvidia profile_id=ag-w1 token=k
|
||
→ ok=True «Сервер nvidia (ag-w1) успешно подключен»
|
||
```
|
||
|
||
Аккаунт NVIDIA записан в слот Antigravity. Бэкенд **не проверяет, что слот принадлежит провайдеру**.
|
||
|
||
Как владелец в это попадает: в мастере для OpenRouter и NVIDIA список слотов пуст — `buildSlotOptions` возвращает «Список слотов ещё не получен». Дальше в `app.js` слот выбирается так:
|
||
|
||
```js
|
||
selectedProfileId = window._wiz_device_profile ?? (deviceSlot?.value || redirectSlot?.value || '');
|
||
```
|
||
|
||
`??` пропускает пустую строку, поэтому побеждает `_wiz_device_profile`, оставшийся **от предыдущей попытки подключения другого провайдера**. Владелец пробовал Antigravity, потом NVIDIA — и NVIDIA легла в `ag-w1`.
|
||
|
||
Отсюда жалобы 3 и 4: «нвидиа не добавляется», «опенроутер так же не добавляется». Он добавляется — не туда.
|
||
|
||
Требуется:
|
||
|
||
1. **Бэкенд отклоняет чужой слот.** `profile_id`, не принадлежащий провайдеру, — отказ с причиной, а не `ok: True`.
|
||
2. **Состояние мастера сбрасывается** при возврате к выбору провайдера и при открытии нового подключения. Остатков от прошлой попытки быть не должно.
|
||
3. **Список слотов для OpenRouter и NVIDIA** заполняется или поле не показывается вовсе, раз слот выдаётся автоматически.
|
||
4. **Прогнать сквозной путь** для обоих провайдеров с заведомо неверным ключом: профиль создаётся с правильным идентификатором, проверка подключения даёт внятную ошибку авторизации.
|
||
|
||
## P0-2. Вернуть разделение по провайдерам
|
||
|
||
Владелец: «нет разделения по аккаунтам. Как раньше: Антигравити и снизу все аккаунты аги, Грок и снизу все аккаунты грока».
|
||
|
||
Разметка группировки цела (`provider-group`, `provider-group-header`, счётчик). Её **скрыл A48**, добавив в `style.css`:
|
||
|
||
```css
|
||
.provider-group,.accounts-grid { display:contents; }
|
||
.provider-group-header { display:none; }
|
||
```
|
||
|
||
Вернуть группы: заголовок провайдера, его значок, число аккаунтов, под ним карточки. Вёрстку A48 в остальном не ломать — это правка одного места в стилях, а не переделка экрана.
|
||
|
||
## P0-3. Проверка должна запускаться сама
|
||
|
||
Владелец: «везде пишет Статус: Не проверялся и, я так понимаю, ничего не работает».
|
||
|
||
Ярлык честен, но вывод владельца неверен, и это вина интерфейса. Проверено:
|
||
|
||
```
|
||
unified_health.py:499 precord.last_success is None → «Не проверялся»
|
||
server.py, hermes_hub_app.py — вызова проверки при запуске НЕТ
|
||
```
|
||
|
||
То есть состояние меняется только после **успешного вызова через профиль**, а вызвать его автоматически некому. Пока владелец не нажмёт «Проверить подключение» вручную для каждого аккаунта, все останутся «Не проверялся» навсегда.
|
||
|
||
Требуется:
|
||
|
||
1. **Проверка запускается сама**: сразу после подключения аккаунта и периодически. Период настраивается, значение по умолчанию обосновать.
|
||
2. **Не блокировать интерфейс**: проверка идёт в фоне, состояние обновляется по мере готовности.
|
||
3. **Различать три состояния явно**: «не проверялся», «проверяется», «проверен: работает / не работает с причиной». Сейчас первое и третье сливаются в одно.
|
||
4. **Кнопка ручной проверки остаётся** — и для отдельного аккаунта, и для всех сразу.
|
||
|
||
## P0-4. Списки моделей не подтягиваются ни у одного аккаунта
|
||
|
||
Та же причина: обнаружение запускается только по явному действию. У Grok, Antigravity и Ollama владелец видит «Список моделей ещё не получен от провайдера».
|
||
|
||
1. **Запрашивать список при подключении** аккаунта и при периодической проверке.
|
||
2. **Кэшировать** с временем получения; показывать, когда список снят.
|
||
3. **Ошибка обнаружения доходит до интерфейса с текстом ответа сервера.** «Не получен» и «сервер отказал: <текст>» — разные сообщения.
|
||
4. **Кнопка «Запросить список моделей» показывает ход** и результат, а не остаётся в прежнем виде.
|
||
|
||
## P0-5. Облачные модели Ollama
|
||
|
||
Ветка обнаружения Ollama после A42 читает адрес из профиля и опрашивает `/api/tags`. Это **только локально скачанные модели**; облачных там нет по устройству эндпоинта.
|
||
|
||
1. Выяснить **по действующей документации Ollama**, как получить список облачных моделей учётной записи и что для этого нужно. **Эндпоинт не выдумывать.**
|
||
2. Показывать локальные и облачные раздельно, чтобы владелец видел, что откуда.
|
||
3. Способ не подтверждён документацией — так и написать в отчёте, а в интерфейсе показать `Н/Д` с причиной. Это принимается; выдуманный адрес — нет.
|
||
|
||
## P0-6. Долгая загрузка данных аккаунта
|
||
|
||
Владелец: «у Грока и Антигравити долго подгружаются данные аккаунтов… чтобы не начали по несколько раз подключать один аккаунт».
|
||
|
||
Измеренные пределы ожидания:
|
||
|
||
```
|
||
quota_collector таймауты 15, 20 и 30 секунд на запрос
|
||
agy_subprocess таймаут 60 секунд — Antigravity ходит через CLI agy
|
||
```
|
||
|
||
То есть до минуты ожидания — это штатное поведение, а не поломка. Проблема в том, что владелец этого не видит.
|
||
|
||
1. **Показывать ход**: «идёт опрос провайдера, это может занять до минуты» с указанием, какой именно аккаунт опрашивается.
|
||
2. **Не давать запустить подключение того же аккаунта повторно**, пока предыдущее не завершилось.
|
||
3. **По истечении ожидания** — внятное сообщение с причиной и предложением повторить, а не молчание.
|
||
4. Ускорять там, где это возможно без риска: параллельный опрос независимых аккаунтов вместо последовательного. Если ускорение невозможно — так и написать, честное объяснение задержки достаточно.
|
||
|
||
## P0-7. Локальный сервер называть тем, что там работает
|
||
|
||
Владелец: «локальный сервер это llama, так и надо подписывать».
|
||
|
||
Сейчас `auto_assigner.py:83` даёт провайдеру `local` подпись «Локальный сервер», а профилям — «Локальный сервер 1» и «Локальный сервер 2».
|
||
|
||
1. Провайдер `local` подписывать по движку: `llama.cpp`. Для `ollama` и `vllm` подписи уже свои — не трогать.
|
||
2. **Если движок определяется по ответу сервера** — брать оттуда. Иначе подпись по типу профиля, без выдумок.
|
||
3. Проверить, что переименование не ломает сохранённые конфигурации: идентификаторы профилей не меняются, меняется только отображаемое имя.
|
||
|
||
## P0-8. Аудит вторым проходом
|
||
|
||
1. **Проверить чужой слот целенаправленно**: подключить NVIDIA после начатой и брошенной попытки Antigravity. Аккаунт обязан лечь в свой слот.
|
||
2. **Убедиться, что мнимых успехов не осталось**: ни одно действие, положившее данные не туда, не возвращает `ok: True`.
|
||
3. **Открыть экран «Аккаунты»** и увидеть группы по провайдерам. Скриншот приложить.
|
||
4. **Дождаться автоматической проверки** и убедиться, что состояние сменилось само, без нажатий.
|
||
5. **Проверить, что «не проверялся» и «проверен, не работает» различимы** на экране.
|
||
6. **Эндпоинт облачных моделей Ollama** сверить с документацией.
|
||
7. **Побочные изменения** объяснить.
|
||
8. **Пропущенный пункт назвать пропущенным.**
|
||
|
||
---
|
||
|
||
## Ограничения
|
||
|
||
- Ключи владельца не запрашивать и в репозиторий не класть.
|
||
- Учётные данные и `~/.hermes/agy_profiles/` не трогать.
|
||
- Вёрстку A48 не переделывать: по группам — правка стилей, не переработка экрана.
|
||
- Службы `qwen-coder` и `qwen-compressor` не трогать.
|
||
- Версию `0.1.1` не поднимать.
|
||
- Правило честности без исключений: не измерено — `Н/Д` с причиной.
|
||
|
||
## Критерии приёмки
|
||
|
||
1. Ветка в `origin`, `git status` чист.
|
||
2. Аккаунт не сохраняется в слот чужого провайдера; попытка отклоняется с причиной; проверено.
|
||
3. Состояние мастера сбрасывается между попытками; проверено сквозным путём.
|
||
4. OpenRouter и NVIDIA подключаются с правильными идентификаторами профилей.
|
||
5. На экране «Аккаунты» вернулись группы по провайдерам; скриншот приложен.
|
||
6. Проверка запускается автоматически после подключения и периодически; состояние меняется без ручных нажатий.
|
||
7. «Не проверялся», «проверяется» и «проверен, не работает» различимы.
|
||
8. Списки моделей подтягиваются автоматически; ошибка доходит с текстом сервера.
|
||
9. Облачные модели Ollama получены либо честно объявлены недоступными с причиной.
|
||
10. Долгая загрузка показывает ход; повторный запуск того же подключения невозможен.
|
||
11. Локальный провайдер подписан по движку.
|
||
12. `ruff check .` чисто; релизный гейт 10/10; тестов не меньше **517**.
|
||
13. Память проекта в AI-Memory обновлена.
|
||
14. Отчёт: `START_HEAD`, `FINAL_HEAD`, `origin/main`, `git status`, `X passed / Y skipped / Z failed`.
|
||
|
||
## Главное
|
||
|
||
Владелец смотрит на четыре подключённых аккаунта, у всех «Не проверялся», ни у одного нет списка моделей, и делает единственно возможный вывод: ничего не работает. На деле проверка просто ни разу не запускалась, потому что запускать её некому.
|
||
|
||
Рядом дефект, который хуже: аккаунт NVIDIA сохраняется в слот Antigravity и докладывает об успехе. Владелец видит, что аккаунт «не добавился», и пробует снова — а в конфигурации накапливается мусор.
|
||
|
||
## Порядок сдачи
|
||
Передать точный `FINAL_COMMIT_SHA`. |