diff --git a/openspec/changes/wiki-module/design.md b/openspec/changes/wiki-module/design.md index 1c2c75d..a1e42db 100644 --- a/openspec/changes/wiki-module/design.md +++ b/openspec/changes/wiki-module/design.md @@ -556,3 +556,27 @@ jira безвреден. экранирует `\ [ ] <` и `_`/`*` на границе слова. `@` не экранируется. Цена ошибки: сырой `.md` с `<`. 56. Известные края (отложены): вложение в `` страницы/внешней ссылки, вложенный `` между `` и ``, хвостовой `\` в тексте ссылки, пробелы/скобки во внешнем href, дубликаты `ref` (побеждает последний). + +Решения исполнителя Task 7 и рулинг R-6 (2026-10-24): + +57. **R-6.** В контракт `CommandHooks` ядра добавлены два необязательных хука: `before_result` (вызывается до + транзакции отчёта; нужен, чтобы перевод и запись файлов шли вне `BEGIN IMMEDIATE`, решение 10) и `abort_result` + (`queue.report_result` вызывает его в `finally`, если отчёт не дошёл до `after_result`). У jira оба `None`. Цена + ошибки: правка контракта модуля; сборку можно вернуть в `on_result` ценой блокировки очереди на время сборки. +58. Идентификаторы вложений выделяются короткой транзакцией до сборки копии; при отбрасывании или сбое добавленные + строки `state='none'` удаляются (`abort_result`). Подготовка хранится в памяти процесса; после рестарта хаба + повтор отчёта готовит заново. Цена ошибки: сироты до следующей синхронизации. +59. Подготовка идёт в `.<имя>.new.` под per-label `Lock` от `before_result` до `after_result`/`abort_result`; + второй одновременный `done` ждёт первого (без таймаута) и затем выходит идемпотентно. `finish_pending_swaps` + продвигает `.new*` только при наличии `_tree.json`. Цена ошибки: долгая сборка проекта задерживает отчёты по нему. +60. `codes[0]` обязан быть корнем команды; страницы без родителя и циклы цепляются к корню; `NN` в имени каталога — + позиция среди соседей (у корня каталог по названию, без номера); дубликаты имён — `_2`, `_3` без учёта регистра; + имя до 80 символов и 200 байт. Цена ошибки: другие имена каталогов. +61. FTS-таблица `wiki_page_fts` создаётся лениво в `search.ensure` (не в `schema.SQL`), эталон `schema` не меняется; + токены запроса — `\w+`. Сбой подмены каталога откатывает строки и переводит команду в `failed`. Падение внешнего + COMMIT после подмены оставляет новые файлы при старых строках до следующей синхронизации. Цена ошибки: лишняя + синхронизация. +62. `failed_at` пишется при `failed`, отброшенной и отменённой синхронизации (иначе автотик ставит пакеты каждый тик); + `housekeeping_tick` удаляет стадию команд не в `queued`/`claimed`. Лимиты `stage`: `code` 200, `title` 1000, `url` + 4000, до 20000 страниц на команду; формат `DOC-\d+` для `code` не навязывается. Пустые `parent_code`/`url` — `None`. + `ValueError` из `before_result` → 500; `sqlite3.OperationalError` из подготовки → 500 (повтор агентом).