|
All checks were successful
CI / changes (pull_request) Successful in 10s
CI Trade-In / changes (pull_request) Successful in 11s
CI / frontend-tests (pull_request) Has been skipped
CI Trade-In / backend-tests (pull_request) Has been skipped
CI Trade-In / frontend-checks (pull_request) Has been skipped
CI / openapi-codegen-check (pull_request) Successful in 2m47s
CI / backend-tests (pull_request) Successful in 15m48s
Схема под решения владельца от 2026-07-31 по эпику «единый вход». Python-кода нет, поведение прода не меняется — в БД auth пока никто не ходит. Развилка А закрыта в пользу ПОЛНОГО переезда: tradein_users (БД tradein) в итоге удаляется, auth.users становится единственным реестром людей. Значит role и manager_id переезжают сюда — это отменяет решение 001:15-19 («ролей здесь нет — сознательно»), что зафиксировано в шапке файла и переписанным COMMENT ON TABLE, а не оставлено расходиться молча. Развилка Б закрыта в пользу трёх состояний: is_active заменён на access_state (active / trial_expired / disabled). Булев флаг схлопывал «пускаем, но объясняем» и «не пускаем вовсе» в одно значение — trial-экран исчезал бы без падения тестов. Семантика зафиксирована в COMMENT: trial_expired при ВЕРНОМ пароле даёт 403 с отдельным кодом и НЕ выдаёт сессию, disabled — generic 401; неверный пароль в любом состоянии остаётся generic 401, то есть защита от перечисления логинов сохраняется. user2 («Брусника») → trial_expired. Колонки role/manager_id зеркалят м.192 побуквенно (CHECK ролей, иерархический CHECK, partial index, self-FK ON DELETE SET NULL), чтобы код «Меры» переехал на auth.users без правок. Добавлен users_manager_not_self_ck — на уровне БД самоназначение менеджером иначе проходит, а второй потребитель (Птица) валидации «Меры» не имеет. Гранты. INSERT выдан — без него переезд не состоится (создание сотрудника из «Команды»). DELETE НЕ выдан: потребителя нет (в team.py только POST и PATCH), а 002:22-33 отклоняла ровно такие гранты-на-будущее; появится хендлер — появится строка GRANT в той же миграции. Табличный UPDATE из 002:80 сужен до column-level: иначе auth_app молча получил бы право писать role и access_state, и ошибка в PATCH-эндпоинте превращалась бы в тихое повышение до админа или тихое снятие блокировки. role и manager_id в список не включены — их сегодня не пишет никто. Гранта на users_id_seq нет намеренно: для GENERATED ALWAYS AS IDENTITY PostgreSQL использует NextValueExpr → nextval_internal(check_permissions := false), ACL последовательности не проверяется. Утверждение 002:26-27 («идентичность требует nextval») фактически неверно; проверено обратным экспериментом — REVOKE, затем INSERT. Проверено исполнением на postgres:16, не по комментариям: - чистая сборка 001→002→003→004 — 13 строк, роли admin/manager×2/employee×10, user2 = trial_expired, is_active отсутствует, все 6 констрейнтов на месте; - повторный прогон 004 ×2 идемпотентен; - ручные прод-правки (user2 → active, user3 → manager) переживают повтор — backfill не затирает решения владельца; - периметр auth_app: INSERT users ✓, UPDATE access_state ✓, INSERT sessions ✓; UPDATE role ✗, UPDATE manager_id ✗, DELETE ✗, CREATE TABLE ✗; - CHECK'и ловят: admin с manager_id, self-manager, access_state вне списка, role вне списка, INSERT без role. Тест: 6 passed. Добавлена проверка запрета CREATE INDEX CONCURRENTLY — в связке с обязательной обёрткой BEGIN/COMMIT это комбинация, невыполнимая на проде (25001), а отдельной проверки на неё не было. |
||
|---|---|---|
| .. | ||
| api | ||
| fixtures | ||
| integration | ||
| scrapers | ||
| scripts | ||
| services | ||
| smoke | ||
| sql | ||
| workers | ||
| __init__.py | ||
| conftest.py | ||
| test_admin_weight_profiles.py | ||
| test_app_logging.py | ||
| test_audit_middleware.py | ||
| test_concepts_stub.py | ||
| test_connection_capacity_loaders.py | ||
| test_eesk_reserve_loader.py | ||
| test_eias_heat_loader.py | ||
| test_ekb_geoportal_client.py | ||
| test_ekgas_outlet_loader.py | ||
| test_gas_grs_loader.py | ||
| test_gate_verdict.py | ||
| test_gisogd66_loader.py | ||
| test_health.py | ||
| test_layout_signature.py | ||
| test_layout_tz_html.py | ||
| test_layout_tz_pdf.py | ||
| test_network_obremenenie.py | ||
| test_network_zone_humanize.py | ||
| test_noise_loader.py | ||
| test_nspd_client.py | ||
| test_nspd_sync.py | ||
| test_ors_client.py | ||
| test_osm_tp_geocoder.py | ||
| test_osrm_client_local.py | ||
| test_ping.py | ||
| test_poi_score.py | ||
| test_quarter_dump_lookup.py | ||
| test_rbac.py | ||
| test_riasurt_sverdl_client.py | ||
| test_saturation.py | ||
| test_sentry_init.py | ||
| test_utility_infrastructure_loader.py | ||
| test_velocity.py | ||
| test_weight_profiles.py | ||