From b3ec23b9a2d77ff406010028fbd01df0e0d2864f Mon Sep 17 00:00:00 2001 From: Andrey Epifancev Date: Sat, 24 Oct 2026 00:26:42 +0400 Subject: [PATCH] =?UTF-8?q?docs(openspec):=20wiki-module=20=E2=80=94=20?= =?UTF-8?q?=D1=80=D0=B5=D0=B0=D0=BB=D1=8C=D0=BD=D1=8B=D0=B5=20=D1=84=D0=BE?= =?UTF-8?q?=D1=80=D0=BC=D0=B0=D1=82=D1=8B=20=D1=81=D1=81=D1=8B=D0=BB=D0=BE?= =?UTF-8?q?=D0=BA=20Eva=20=D0=B8=D0=B7=20=D0=B2=D1=8B=D0=B3=D1=80=D1=83?= =?UTF-8?q?=D0=B7=D0=BA=D0=B8=20=D0=A2=D0=97=20(#91)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-Authored-By: Claude Opus 5.5 --- openspec/changes/wiki-module/design.md | 25 ++++++++++++++++--- .../changes/wiki-module/specs/wiki/spec.md | 20 +++++++++++---- 2 files changed, 37 insertions(+), 8 deletions(-) diff --git a/openspec/changes/wiki-module/design.md b/openspec/changes/wiki-module/design.md index f187de6..5089da3 100644 --- a/openspec/changes/wiki-module/design.md +++ b/openspec/changes/wiki-module/design.md @@ -35,7 +35,18 @@ Дерево строится локально по `parent`/`tree_parent` из списка всех документов проекта Eva. Фильтр `parent.code` API не принимает (-32001). Если у страницы нет `project`, дерево обходится в ширину через фильтр `tree_parent.code`. Картинки и файлы — ссылки ``/`` на тот же хост с путём `/(files?|attachments?|download|media|upload)`. -Всё это обкатано в `eva_wiki_export.py` (корень workspace). Есть ли у документа дата изменения и история версий, +Всё это обкатано в `eva_wiki_export.py` (корень workspace). + +Реальные форматы ссылок взяты из выгрузки ТЗ АРМ КА (`awp-ca/docs/source/tz/`, корень DOC-019855, 22 страницы, 388 КБ +Markdown; сырого HTML в выгрузке нет): +- **Ссылка на страницу** — относительный адрес без хоста и без ведущей `/`: `project/Document/DOC-019834`. +- **Картинка** — `/files/obj/CmfDocument/CmfDocument%3A<3 символа>/CmfDocument%3A/<имя в URL-кодировке>?version=1`. +- **Файл, прикреплённый к странице** (xlsx, dbml), выглядит как миниатюра `…/<имя файла>.meta/thumbnail.jpg?version=1`, + значок `static/attach-file.png`, имя файла и дата текстом. Ссылка на сам файл в выгрузке не сохранилась: её, + вероятно, съел markdownify. Адрес файла — адрес миниатюры без `.meta/thumbnail.jpg`. +- **`static/…`** — ресурсы интерфейса Eva, не вложения. + +Объём настоящего дерева невелик (десятки страниц), но решения ниже рассчитаны и на сотни. Есть ли у документа дата изменения и история версий, неизвестно: публичной документации API нет, Eva доступна только из сети банка. Владелец (brainstorming 23–24.10.2026): см. proposal, «Why». @@ -205,8 +216,12 @@ jira безвреден. 1. Берёт корень `CmfDocument.get` и все страницы поддерева, как `collect_subtree` в `eva_wiki_export.py`. 2. По каждой странице берёт `text`. 3. Разбирает ссылки страницы. Это делает агент, а не хаб: только он знает `eva.base_url`. - - **Вложение** — ``/`` на хост Eva с путём по правилу из Context. - - **Ссылка на страницу** — ссылка на хост Eva с кодом `DOC-<цифры>` в адресе. + Относительные адреса относятся к хосту Eva (`urljoin` с `eva.base_url`). + - **Вложение** — ``/`` на хост Eva с путём `/files/…`. + - Миниатюра `<адрес>.meta/thumbnail.jpg` — это файл по `<адрес>`; одно вложение, а не два. + - Адрес файла и его миниатюры в одной странице — одно вложение. + - `static/…` (значки интерфейса) не вложение: ссылка удаляется из текста. + - **Ссылка на страницу** — ссылка на хост Eva с кодом `DOC-<цифры>` в адресе (`project/Document/DOC-…`). - По каждой ссылке агент шлёт: - `ref` — значение атрибута ровно как в HTML, по нему хаб находит место замены; - `url` — абсолютный адрес (только у вложения); @@ -432,3 +447,7 @@ jira безвреден. 16. **Смена корня отменяет невыданные `wiki_sync`, поздний `done` старого корня отбрасывается** (решение 10; builder check). Обоснование: корень правят, пока eva-agent ещё не установлен; копия старого дерева не должна встать под новый корень. Цена ошибки — лишняя синхронизация. +17. **Тестовые HTML-страницы — синтетические, по реальным форматам адресов из `awp-ca/docs/source/tz/`** (Context). Сам + текст ТЗ в фикстуры не копируется. Обоснование: сырого HTML Eva нет, а содержимое ТЗ банка не место в репозитории + хаба. Цена ошибки — разметку вокруг ссылок (особенно у прикреплённых файлов) уточнять по первой живой + синхронизации; агент и хаб правятся вместе. diff --git a/openspec/changes/wiki-module/specs/wiki/spec.md b/openspec/changes/wiki-module/specs/wiki/spec.md index 2dc8758..307a82d 100644 --- a/openspec/changes/wiki-module/specs/wiki/spec.md +++ b/openspec/changes/wiki-module/specs/wiki/spec.md @@ -83,10 +83,11 @@ links: [{ref, code}]}`, где `attachments` — ссылки и картинк корне копии — `_tree.json`, список `{code, title, depth, path}` в порядке обхода. Копия SHALL собираться рядом (`wiki/.<метка>.new/`) и подменять прежнюю переименованием; незавершённую подмену хаб SHALL доводить при старте. -HTML страницы SHALL переводиться в Markdown (заголовки `#`); ссылка или картинка на файл Eva (по списку `attachments` агента: тот же хост, путь с -`files`, `file`, `attachments`, `attachment`, `download`, `media` или `upload`) SHALL заменяться на -`[📎 <имя>](attachment:)`, где `id` — строка вложения; ссылка на документ Eva с кодом `DOC-<цифры>` — на -`[<текст>](page:<код>)`; прочие ссылки остаются. Сырой HTML в копию не попадает. +HTML страницы SHALL переводиться в Markdown (заголовки `#`); ссылка или картинка на файл Eva (по списку `attachments` агента: адрес на хосте Eva +с путём `/files/…`, относительный адрес — тоже Eva; миниатюра `<адрес>.meta/thumbnail.jpg` означает файл `<адрес>`, а +ссылки на `static/…` — значки интерфейса — из текста удаляются) SHALL заменяться на +`[📎 <имя>](attachment:)`, где `id` — строка вложения; ссылка на документ Eva с кодом `DOC-<цифры>` (в Eva — относительный +`project/Document/DOC-…`) — на `[<текст>](page:<код>)`; прочие ссылки остаются. Сырой HTML в копию не попадает. #### Scenario: Раскладка - **WHEN** корень DOC-1 «АРМ КА», дети DOC-3 «Статусы» (`orderno` 1) и DOC-2 «Роли/права» (`orderno` 2) @@ -94,9 +95,18 @@ HTML страницы SHALL переводиться в Markdown (заголов DOC-1, DOC-3, DOC-2 #### Scenario: Картинка на странице -- **WHEN** в HTML DOC-3 `` того же хоста +- **WHEN** в HTML DOC-3 `` - **THEN** в `index.md` — `[📎 scheme.png](attachment:)`, у вложения `` `state = none`, файл не скачан +#### Scenario: Прикреплённый файл с миниатюрой +- **WHEN** на странице миниатюра `…//model.xlsx.meta/thumbnail.jpg?version=1`, значок `static/attach-file.png` и + ссылка на `…//model.xlsx` +- **THEN** одно вложение `model.xlsx` с адресом файла; в тексте одна ссылка `[📎 model.xlsx](attachment:)`, значка нет + +#### Scenario: Ссылка на другую страницу +- **WHEN** в HTML `Модель данных` +- **THEN** в `index.md` — `[Модель данных](page:DOC-019834)` + ### Requirement: Вложения вики по запросу `POST /wiki/attachments/{id}/fetch` SHALL ставить пакет из одной команды чтения `wiki_fetch {attachment_id, url}` и переводить вложение в `fetching`; для `fetching` — ответ текущим состоянием без нового пакета, для `ready` — сразу