diff --git a/frontend/docs/BACKLOG.md b/frontend/docs/BACKLOG.md index 042bbfac..15d4aac8 100644 --- a/frontend/docs/BACKLOG.md +++ b/frontend/docs/BACKLOG.md @@ -64,6 +64,6 @@ | Ф-58 | **RTL не проверен ни разу, а триггер наступил.** Условие, записанное S1 («когда появится `I18nProvider`»), исполнилось в S3.7: провайдер стоит, локаль берётся из стора, `` следует выбору. Чего нет — ни одного прогона с языком письма справа налево: примитивы react-aria логическое направление поддерживают, а НАША раскладка (фиксированное место бейджа, обрезка вкладок, инсеты панелей, стрелка `zh → ru` в статус-полосе) написана в физических терминах местами. Цена вопроса неизвестна до замера; сам замер дешёвый — второй каталог-заглушка плюс `dir="rtl"` и прогон сцен. Делать, когда владелец назовёт второй язык (В-9): до того это проверка обещания, которого продукт не давал | владелец (В-9) → отдельный проход | аудит-свип 14.08 → S4 | | ~~Ф-59~~ | ~~**Спойлер банка достаётся поиском по странице — ЗАМЕРЕНО.**~~ — **ЗАКРЫТА решением владельца 16.08 (D39.138 п.2к): спойлер это ВЕЖЛИВОСТЬ, сделанного достаточно, цена названа.** Сам замер (S4, браузер, `/showcase`, вкладка «Банк»): размытие глифов (`filter: blur`) прячет описание от глаза, но текст остаётся текстом страницы — закрытое описание лежит в `document.body.innerText`, `window.find()` его находит, то есть Ctrl+F подсвечивает закрытую ячейку; скринридер отрезан честно (`aria-hidden`), выделение мышью пусто, под `@media print` размытие СОХРАНЯЕТСЯ (`blur(3px)`), но текстовый слой PDF строится из DOM, и там строка остаётся | закрыт | замер S4 14.08 → D39.138 | | Ф-60 | **Канвас-замер ширин не знает языка строки.** Ширины столбцов банка меряются канвасом одним шрифтом на весь набор (`ui/Table.tsx`), а при ДВУХ CJK-лицах в стеке один и тот же код-пойнт рисуется по-разному: японская и китайская гарнитуры дают разную метрику для общего иероглифа. Сегодня это спит: пара одна (`zh→ru`), лицо одно. Сработает в день, когда в наборе окажутся и `zh`, и `ja` — то есть ровно на второй паре, которую движок уже умеет. Лечение: мерить с тем же `lang`, что у ячейки (канвасу `lang` не передашь — придётся мерить в DOM либо держать по замерщику на язык), и это отдельный проход с пере-замером цены | триггер: вторая пара в одной библиотеке | аудит-свип 14.08 → S4 | -| Ф-61 | **Платформа отвечает по-английски, а интерфейс русский.** Контракт 0.2.3 клал фразу отказа на СЕРВЕР (`Problem.title`/`detail` — «product language», клиент показывает как пришло), и живая платформа слала `"The file is larger than this service accepts"` рядом с русским советом — два языка на одном экране. ⚠ **РЕШЕНО владельцем, вариант B (D39.138 §8 п.4; требование интернациональности подтверждено D39.176 п.4):** на проводе машинный `code` + `request_id`, `title`/`detail` developer-facing, а ФРАЗУ рисует клиент по словарю кодов и локали — таблица `AddBook.tsx:282-288` становится нормой, а фолбэки `AddBook.tsx:289` (`problem?.detail ?? problem?.title`), `Loaded.tsx:66` и `RunStart.tsx:188` при разморозке СНИМАЮТСЯ. Карта «код → фраза» — приложение А компаньона контракта | разморозка: словарь кодов вместо серверной фразы | S4 14.08 → D39.138 | +| Ф-61 | **Платформа отвечает по-английски, а интерфейс русский.** Контракт 0.2.3 клал фразу отказа на СЕРВЕР (`Problem.title`/`detail` — «product language», клиент показывает как пришло), и живая платформа слала `"The file is larger than this service accepts"` рядом с русским советом — два языка на одном экране. ⚠ **РЕШЕНО владельцем, вариант B (D39.138 §8 п.4; требование интернациональности подтверждено D39.176 п.4):** на проводе машинный `code` + `request_id`, `title`/`detail` developer-facing, а ФРАЗУ рисует клиент по словарю кодов и локали — таблица `AddBook.tsx` (греп по предмету) становится нормой, а фолбэки `AddBook.tsx` (греп по предмету) (`problem?.detail ?? problem?.title`), `Loaded.tsx` (греп по предмету) и `RunStart.tsx` (греп по предмету) при разморозке СНИМАЮТСЯ. Карта «код → фраза» — приложение А компаньона контракта | разморозка: словарь кодов вместо серверной фразы | S4 14.08 → D39.138 | | Ф-62 | **Переименовать книгу нечем.** В 0.2.3 `POST /books` клал название один раз (рукой или из имени файла), дальше только чтения. Найдено адверсариальным ревью S4: подсказка формы обещала «название можно будет поправить позже» — обещание, которого контракт не давал; фраза исправлена, обещание снято. ⚠ **ОТВЕТ ПРИШЁЛ (Б-5, канон 0.3.0+):** `PATCH /books/{bookId}` ТОЛЬКО с `title` (409 при живом прогоне) и `DELETE`; правка — отображение, до движкового брифа не доезжает. Плюс слово владельца 16.08 (Б-23): жанр из продукта УХОДИТ совсем — поле формы снять при разморозке | разморозка: правка названия и удаление на живых ручках | S4 14.08 → канон | | Ф-63 | **Рамка поля ввода на модальной поверхности — 1.20:1, ниже порога 1.4.11.** Замер S4 (найдено адверсариальным ревью на новом чекбоксе, у которого рамка — единственный носитель границы; там починено локально на `--color-text-muted`, 3.29:1): `--color-border` `#2e2e2e` о `--color-elevated` `#202020` даёт **1.20:1** при пороге 3:1 для границ элементов управления. Тот же токен несёт рамку ВСЕХ полей формы (`ui/Field.module.css`, модификатор `.framed`), рамку самого модального окна и разделители секций, поэтому одним значением это не чинится: поднять токен — перекрасить всю оболочку, принятую владельцем по референсу (S3.6). Правильный ход — отдельный токен границы для того, что является КОНТРОЛОМ (поле, чекбокс), и он у него уже есть в частном виде. Отложено сознательно: перекраска рамок — это вид, а вид принимает владелец | владелец + отдельный проход | S4 14.08, адверсариальное ревью |