tasks: заведён урожай ревью remove-telegram-intake
- шесть записей по кластерам причин: журнал под внешним значением, нулевой код ответа в журнале, затирание вложения бедным ответом, открытый анониму адрес подтверждения почты, рубеж расшифровки без работы, пределы длительности - находка про код 500 у отказа приёма дописана в json-api-for-spa: там живёт единая точка отображения доменной ошибки - telegram-account-link и bot-api-only-through-bot-client оставлены с оговоркой, что предмета у них нет до возвращения входа
This commit is contained in:
@@ -0,0 +1,66 @@
|
||||
# 🐞 Не давать отправителю задавать, что уедет в журнал
|
||||
|
||||
- **Тип:** fix
|
||||
- **Категория:** Очередь — Заведена урожаем ревью и встала в конец машинально: место в плане стройки назначает человек.
|
||||
- **Зачем:** Путь запроса уезжает в журнал целиком: аноним пишет туда до мегабайта своего текста одной строкой, а хвост имени файла приезжает внутри чужого текста ошибки вместо своего поля.
|
||||
- **Теги:** review-2026-08-15
|
||||
|
||||
Длину и содержимое строки журнала задаёт тот, кто прислал запрос, а не сервис.
|
||||
|
||||
Мест два, причина одна. Слой журнала пишет путь запроса полем `http.route`
|
||||
целиком: приведение режет только последний сегмент и только у ссылок на файлы.
|
||||
Отказ подготовки рабочей копии пересказывает отказ библиотеки целиком, а тот
|
||||
несёт полное имя временного файла — вместе с расширением, взятым из имени
|
||||
отправителя.
|
||||
|
||||
Журнал в этом проекте — место, где наблюдаются инварианты: по нему видно
|
||||
недоставку, остановку конвейера и молчаливый выход из шага. Вытесненный чужим
|
||||
текстом, он перестаёт отвечать на вопрос, ради которого заведён.
|
||||
|
||||
Класс проект уже назвал недопустимым в приведении отказа провайдера входа
|
||||
([conventions/logging.md](../../docs/conventions/logging.md)): «без приведения
|
||||
аноним пишет в журнал что угодно и сколько угодно». Здесь тот же канал шире и
|
||||
дешевле — сессия для него не нужна.
|
||||
|
||||
## Воспроизведение
|
||||
|
||||
**Путь запроса.** Поднять сервис и послать запрос, чей путь длиной 900 000 байт:
|
||||
|
||||
```
|
||||
python3 -c 'socket … GET /<900000×"A"> HTTP/1.1'
|
||||
```
|
||||
|
||||
Ответ — `404`, журнал вырастает с 1048 до 901 194 байт одной строкой. Потолок
|
||||
замерен: 1 048 000 байт ещё проходят, 1 100 000 отвергаются кодом `431`.
|
||||
Внедрения строк при этом нет — библиотека журнала квотирует значение.
|
||||
|
||||
**Хвост имени.** Принять запись, чьё имя несёт 280 байт после последней точки.
|
||||
Отказ подготовки рабочей копии приезжает в журнал уровня `ERROR` строкой вида
|
||||
`error="failed to create work file: open /tmp/transcriber-<число>.<280 байт>:
|
||||
file name too long"`, и поля `file_ext` в ней нет вовсе.
|
||||
|
||||
## Затрагивает
|
||||
|
||||
- слой журнала запроса в `main.go` и приведение пути `journalRoute`;
|
||||
- отказ подготовки рабочей копии в `internal/service`, шаг приёма записи;
|
||||
- `docs/conventions/logging.md` — правило о длине поля журнала;
|
||||
- умолчание `MaxHeaderBytes` у сервера: сегодня оно единственное неназванное
|
||||
рядом с названным сроком чтения.
|
||||
|
||||
## Критерии приёмки
|
||||
|
||||
- Путь запроса в журнале не длиннее объявленного предела, и усечение видно в
|
||||
самой строке. Оракул: тот же запрос с путём в 900 000 байт — прирост журнала
|
||||
не превышает предела, а маршрут по первым байтам по-прежнему различим.
|
||||
- Отказ подготовки рабочей копии не пересказывает отказ библиотеки: расширение
|
||||
идёт своим полем. Оракул: проверка приёма с длинным хвостом имени — строки с
|
||||
этим хвостом в журнале нет, поле `file_ext` есть.
|
||||
- Правило записано конвенцией: длину поля журнала не задаёт вызывающий. Оракул:
|
||||
строка в `docs/conventions/logging.md` и ссылка на неё из обеих правок.
|
||||
|
||||
## Рамки
|
||||
|
||||
Приведение пути не должно делать маршрут неразличимым: по журналу отличают
|
||||
`/api/audio` от `/api/status/:id`. Найдено прогоном ревью задачи
|
||||
`remove-telegram-intake` 2026-08-15, враждебный проход; дефект существовал до той
|
||||
правки, и владелец решил вынести его задачей.
|
||||
Reference in New Issue
Block a user