- storage-without-pocketbase закрыта как реализованная: приёмка сошлась по всем
пяти критериям записи и по двенадцати приёмочным свойствам рубрики ревью
дизайна, работа лежит коммитом c9b7765
- урожай триажа ревью развёрнут в одиннадцать записей с тегом партии
review-2026-08-23 и расставлен по зависимости, а не в конец списка
- находка про признак живости воркера слита в stalled-pipeline-metric: у неё та
же причина — вставший конвейер неотличим от простоя
52 lines
4.0 KiB
Markdown
52 lines
4.0 KiB
Markdown
# 🧹 Разобрать мелочи хранилища на sqlite
|
||
|
||
- **Тип:** chore
|
||
- **Категория:** Очередь — Мелочи слоя хранилища разбираются, пока слой в руках
|
||
- **Зачем:** Четыре мелочи ниже потолка триажа в одном пакете: три репозитория не переводят sql.ErrNoRows в доменную ошибку, два числа задают один и тот же предел страницы порознь, Append не заполняет время, которое сам же кладёт в базу, а у selectList — мёртвый довод prefix.
|
||
- **Теги:** review-2026-08-23
|
||
|
||
Четыре мелочи ревью change `2026-08-23-storage-without-pocketbase`, оставшиеся
|
||
ниже потолка триажа. Собраны одной задачей: все живут в
|
||
`internal/adapter/repo/sqlite` и правятся одним заходом.
|
||
|
||
1. **Репозитории текста, структуры и попытки распознавания не переводят
|
||
`sql.ErrNoRows` в доменную ошибку**, при том что репозиторий записи в том же
|
||
пакете правило исполняет (`record_repo.go`). Вызывающий не отличает «записи
|
||
нет» от отказа базы, потому что типизированного значения ему не приходит.
|
||
2. **Два числа об одном пределе страницы:** `defaultListLimit = 30` в слое
|
||
хранилища и `DefaultPageLimit = 30` в контракте. Совпадают дословно, а
|
||
меняются порознь.
|
||
3. **`RecordEventRepository.Append` не заполняет `event.CreatedAt`**, хотя само
|
||
же значение кладёт в базу: вызывающий получает событие с нулевым временем.
|
||
4. **Мёртвый довод `prefix` у `selectList`** — ни один вызов его не читает.
|
||
|
||
Нашёл проход `review-code` (C6 и то, что осталось за его потолком конвенций).
|
||
|
||
## Затрагивает
|
||
|
||
- `internal/adapter/repo/sqlite` — `text_repo.go`, `recognition_repo.go`,
|
||
`record_event_repo.go`, `record_list.go`;
|
||
- `internal/contract` — типизированное значение «записи нет» и константа
|
||
предела страницы;
|
||
- конвенция [errors.md](../../docs/conventions/errors.md) — единая точка
|
||
трансляции ошибки хранилища.
|
||
|
||
## Критерии приёмки
|
||
|
||
- «Записи нет» приходит вызывающему одним значением из всех репозиториев.
|
||
**Оракул:** тест на каждый из трёх репозиториев — запрос несуществующего
|
||
идентификатора отвечает значением, которое узнаётся `errors.Is`, а не
|
||
`sql.ErrNoRows`.
|
||
- Предел страницы объявлен одним числом. **Оракул:** `grep -rn "= 30"
|
||
internal/` — объявление одно, второе место ссылается на него.
|
||
- Приложенное событие приходит с временем, которое уехало в базу. **Оракул:**
|
||
тест `Append` — у возвращённого события `CreatedAt` не нулевое и совпадает со
|
||
строкой в базе.
|
||
- Мёртвого довода нет. **Оракул:** `go vet ./...` и `golangci-lint run`
|
||
зелёные, `grep` по `selectList` не находит довода `prefix`.
|
||
|
||
## Рамки
|
||
|
||
Раскладку каталога данных и имена копий не трогаем — это разведка
|
||
`record-file-name-readability`. Применённые шаги схемы не переписываются.
|