Files
autotest/DOCS/api-operation-stages.md
T

5.8 KiB
Raw Blame History

Стадии выполнения операции (stages)

Как через API и код Autotest определить, на каком этапе исполнения находится команда (операция).

Связь с реальным кодом

Компонент Файл Роль
Запуск операции app-autotest/site/operations/executor.pyexecute_operation() Создаёт операцию и возвращает op_uid
Поллинг (async / sync) app-autotest/site/operations/poll.pypoll_until_done() Периодически спрашивает статус и отдаёт stages
Фоновый поллинг + кэш app-autotest/site/routes/api_test.py_finish_op(), _op_results Ждёт dtFinish, кладёт stages в кэш
Отдача в UI app-autotest/site/routes/api_test.pyapi_test_status() GET /api/test/status/<op_uid>stages
Вывод этапов (ручной режим) app-autotest/site/static/js/operations.jsshowStages() Поллинг каждые 2 сек + отрисовка
Вывод этапов (история) app-autotest/site/static/js/history.jsrenderStages() Раскрытие строки истории по клику

Эндпоинты

1. Запуск операции (получаем opUid)

POST /api/test

execute_operation() проходит этапы запуска:

  1. CREATE: POST /instancesinstanceUid
  2. CREATE + NON-CREATE: POST /instanceOperationsopUid
  3. Параметры: send_params_terraform(...)
  4. POST /instanceOperations/{opUid}/run → запуск

Возвращает {ok, error, failed_step, instance_uid, op_uid, display_name}. При ok=False смотри failed_step: instances / instanceOperations / params / run.

2. Поллинг статуса (определяем этап)

GET /api/test/status/<op_uid>

Ответ — dict, ключи:

  • status"RUNNING" / "OK" / "FAIL"
  • done — bool, завершена ли операция
  • stages — список этапов
  • isInProgress, isSuccessful, duration, errorLog, displayName

Сервер сам дергает Nubes API:

GET /instanceOperations/{opUid}?fields=dtFinish,isSuccessful,errorLog,isInProgress,duration,stages

3. Фоновый поллинг (для сценариев/сохранения)

poll_until_done() поллит тот же эндпоинт и возвращает:

{status, is_successful, error_log, stages, duration, svc}

где status ∈ {"OK", "FAIL", "TIMEOUT"}.

Как определить текущий этап

Поле stages — массив объектов-стадий. Каждая стадия:

Поле Тип Описание
instanceOperationStageUid UUID UID стадии
stage string Название (напр. "1. Валидация")
isSuccessful bool/null true/false/null (ещё не завершена)
dtStart datetime Начало этапа
dtFinish datetime/null Окончание (null — ещё идёт)
duration float Секунды (пересчитывается, пока идёт)
stageMsg JSON-string/null Детальные логи этапа

Правило определения текущего этапа:

  • dtFinish == null (или isSuccessful == null) → этап сейчас выполняется — это текущий этап команды.
  • dtFinish != null → этап завершён (isSuccessful == true, false).
  • Идёшь по массиву по порядку: до первого dtFinish == null — уже прошли, первый с null — текущий, дальше — ещё не начались.

Завершение операции: смотри done / isInProgress. Когда done == truestatus принимает OK/FAIL. При FAIL текст ошибки в errorLog / error_log.

Пример ответа

{
  "status": "RUNNING",
  "done": false,
  "stages": [
    { "stage": "1. Валидация",        "isSuccessful": true,  "dtFinish": "2026-07-24T15:22:01.804+0300", "duration": 4.4 },
    { "stage": "2. Основной процесс", "isSuccessful": null,  "dtFinish": null, "duration": 14.1 },
    { "stage": "3. Проверки",         "isSuccessful": null,  "dtFinish": null }
  ]
}

Здесь: этап 1 завершён , этап 2 — текущий (идёт), этап 3 — ещё не начался.

Вывод этапов в UI

Ручной режим (operations.jsshowStages())

  • Поллинг: setInterval каждые 2 секундыGET /api/test/status/{opUid}
  • showStages(sd.stages) рендерит этапы в последний .stages-box:
    • иконка: (завершён успешно) / (завершён с ошибкой) / (идёт)
    • название stage + длительность duration
  • stopPoll() после завершения; при 5 ошибках подряд поллинга → TIMEOUT

История (history.jsrenderStages())

  • GET /api/history → записи, у каждой поле stages
  • по клику на строку раскрываются этапы (stages сохранены в БД runs, колонка stages JSONB)

Примечание

stageMsg содержит JSON-строку с массивом [[заголовок, текст], ...] — можно распарсить и показать детальные логи этапа.