## Why

«Единое окно» реализовано наполовину: jellybit распознаёт **ручное** удаление и
метит рассинхрон (`state-reconciliation` — `target_missing`/`orphaned`/`deleted`,
безопасный `Undo` с гардом последней копии, preflight). Не хватает второй
половины — **удалять загрузку из самого jellybit**, не идя руками в
qBittorrent/Jellyfin.

Основной сценарий одного окна — «досмотрел → освободить место»: убрать и раздачу,
и файлы в библиотеке разом. Из-за хардлинков иначе место не вернуть — файл в
`downloads/` (qBittorrent) и наша ссылка в библиотеке указывают на **один инод**,
диск освобождается только когда исчезает последняя ссылка. Значит удаление обязано
снять **обе** стороны. Это осознанный выход за инвариант «источник неприкосновенен»,
поэтому — с подтверждением и отдельным следом в логе/причине перехода.

`Undo` и `delete` — разные операции, и это надо зафиксировать:

- **Undo** — «перераспознать»: снимает только наши ссылки, раздачу в qBittorrent
  сохраняет, гард последней копии **включён**. Уже готов.
- **delete** — «убрать окончательно, освободить место»: снимает наши ссылки И
  сносит раздачу+файлы из qBittorrent, гард **выключен**, состояние терминальное
  `deleted`.

## What Changes

- Ввести пользовательскую команду **«Удалить»** в `worker`, доступную из
  `done`, `orphaned`, `target_missing` (подчистить остатки за собой из любого
  состояния «уже разложено / рассинхрон»). Действие: снять наши библиотечные
  хардлинки последнего батча (переиспользуем механику `Undo`, `superseded`
  пропускаем) с **выключенным** гардом последней копии **+** удалить раздачу с
  файлами из qBittorrent. Идемпотентно к отсутствующей стороне (в `orphaned` нет
  источника, в `target_missing` нет цели).
- Переиспользовать существующее терминальное состояние `deleted` — **без** нового
  статуса; рёбра `done/orphaned/target_missing → deleted` уже есть в
  `allowedTransitions`. Инициатора-пользователя отличать от сверки через
  `error_code = "user_delete"` (сверка кладёт `"reconcile"`), человекочитаемую
  причину — в `error_msg` и лог перехода.
- Добавить в `qbt` метод удаления раздачи (`POST /api/v2/torrents/delete`,
  `deleteFiles=true`) и объявить его в интерфейсе `QBittorrent` воркера.
- Добавить в `layout` путь снятия ссылок **без** гарда последней копии (delete
  сознательно снимает последнюю копию, в отличие от `Undo`).
- Обязательное **подтверждение** во всех транспортах: веб-UI — danger-секция с
  кнопкой в самом низу страницы загрузки; Telegram — двухшаговый inline-confirm.

## Capabilities

### New Capabilities
<!-- нет новых capability -->

### Modified Capabilities
- `state-reconciliation`: добавляется пользовательская команда «Удалить»
  (снять источник и цель, гард последней копии выключен) с переходом
  `done`/`orphaned`/`target_missing` → терминальный `deleted`, отличимая от
  reconcile-`deleted` инициатором, с обязательным подтверждением.

## Impact

- Код воркера: `internal/worker/review.go` (новый метод `Delete`; путь снятия
  ссылок с выключенным гардом), `internal/worker/worker.go` (расширить интерфейс
  `QBittorrent` методом удаления; проброс в конструктор при необходимости).
- Инфраструктура: `internal/qbt/qbt.go` (метод `Delete(hashes, deleteFiles)` →
  `/api/v2/torrents/delete`), `internal/layout/layout.go` (снятие ссылок без
  `ErrLastCopy`).
- Транспорты: `internal/httpapi` (роут `POST /ui/downloads/{id}/delete` + confirm,
  флаг `Deletable` по состоянию; опц. JSON-роут), `web/templates/partials`
  (danger-секция внизу страницы загрузки), `internal/tgbot` (действие `delete` +
  двухшаговый confirm-keyboard).
- Данные: **осознанное** снятие последней копии данных при удалении из
  `orphaned` — только по явному подтверждению; инвариант «источник
  неприкосновенен» обходится намеренно и логируется как пользовательское
  удаление. Схема БД не меняется (переиспользуем `error_code`/`error_msg`).
- Тесты: `internal/worker/review_test.go` (delete из каждого из трёх состояний,
  идемпотентность к отсутствующей стороне, отказ из прочих состояний),
  `internal/qbt/qbt_test.go` (форма запроса delete), транспортные тесты confirm.
