Миграция 00004: таблицы `messages`, `message_reactions`,
`channel_read_states`, `files`, `invites` и виртуальная таблица `messages_fts`
с триггерами синхронизации (AGENT.md 6.1, 7.6, 7.7, 7.9, 7.15, 7.16).
Полнотекстовый поиск требует сборки с тегом `sqlite_fts5`:
- `GO_TAGS ?= sqlite_fts5` в Makefile (build/test/cover) и в Dockerfile;
- build-tags в golangci-lint;
- страж `internal/database/fts5_guard.go`: сборка без тега падает с понятным
текстом, а не ломается на миграции в рантайме.
- internal/bootstrap: создание инстанс-админа, главного сервера, ролей
«Администратор» и «Пользователь» (all permissions / дефолтный набор §6.3),
общей текстовой комнаты; повторный запуск идемпотентен
- админ получает флаг is_instance_admin и системный бейдж instance_admin
- CLI: glchat bootstrap-admin, reset-password, make-admin, remove-admin
(работают внутри контейнера через DATA_DIR)
- auth: UserByEmail, SetPassword (отзывает сессии), RegisterAdmin (в обход
флага регистрации — bootstrap выполняет установщик)
- тесты: создание админа и главного сервера, идемпотентность, автовступление
нового пользователя с ролью @user
- регистрация: политика пароля (≥10 + локальный словарь 10k утечек, SecLists MIT),
username и email без учёта регистра, шифрование email с привязкой к аккаунту,
blind index для поиска, автовступление в главный сервер с ролью @user
- вход: Argon2id+pepper, TOTP при включённом 2FA, блокировка после серии неудач,
события безопасности; единый ответ на неверный пароль и неизвестный аккаунт
- сессии: opaque-токены (в БД только SHA-256), ротация токена, logout/logout-all,
отзыв остальных сессий при смене пароля, step-up с окном 10 минут
- 2FA: настройка секрета с QR-URL, подтверждение кодом, 8 резервных кодов
(хранятся хэшами), обязательность для инстанс-админов, запрет отключения
- тесты на реальной SQLite: регистрация/вход/дубликаты, слабые и утёкшие пароли,
ротация и logout-all, TOTP и резервные коды, step-up, смена пароля,
выключенная регистрация, отсутствие секретов в логах
- .golangci.yml: набор линтеров под требования §14 (gosec, gocritic, sloglint,
noctx, revive, depguard для запрета циклических зависимостей internal/*)
- gofumpt вынесен из formatters golangci-lint v2.13 (сообщал о расхождениях,
которые сам же не устранял) и применяется отдельным инструментом
- make fmt/go-lint: проверка gofumpt + golangci-lint fmt --diff
- scripts/gitleaks-scan.sh: поддержка gitleaks 8.19+ (dir) и старых версий (detect)
- исправлены замечания линтеров: обработка ошибок Close, контекст в логах,
NewRequestWithContext в тестах, комментарий к blank-import драйвера SQLite