web-ui: добавлена страница группового удаления загрузок

- выбор → поимённое подтверждение → отчёт: пачка до 20 загрузок, гарды входа
  на обеих границах, потолок времени и остановка после трёх подряд отказов
  внешнего сервиса
- допуск полного удаления сведён в единую точку store.State.CanDelete() —
  worker, страница загрузки и Telegram больше не держат своих перечней
This commit is contained in:
av
2026-08-10 17:43:36 +03:00
parent a7c1efd8eb
commit 288be8ec34
35 changed files with 3185 additions and 31 deletions
+17
View File
@@ -84,6 +84,23 @@ func (s State) IsObservable() bool {
return !s.IsTerminal() || slices.Contains(selfHealingStates, s)
}
// deletableStates — состояния, из которых человеку доступно полное удаление
// (снять библиотечные ссылки + снести раздачу с файлами из qBittorrent).
// Единственный дом перечня: на него смотрят и допуск в ядре (worker.Delete), и
// все транспорты, решающие, показывать действие или нет.
var deletableStates = []State{
StateDone, StateOrphaned, StateTargetMissing,
}
// CanDelete сообщает, допускает ли состояние полное удаление загрузки
// пользователем. Транспорт спрашивает его, чтобы не завести своего перечня
// состояний; проверку в ядре это не заменяет — допуск обязан держаться без
// транспорта (см. openspec/specs/state-reconciliation, «Полное удаление
// загрузки пользователем»).
func (s State) CanDelete() bool {
return slices.Contains(deletableStates, s)
}
// allowedTransitions — декларативный граф легальных переходов машины состояний
// (from → множество допустимых to). Единственный источник истины о легальности
// рёбер: покрывает все переходы, которые worker выполняет по всем capability