"""Политика видимости на API ГК (spec directory-policy): филиал видит своё, чужое — 404, создание из филиала.""" import uuid import httpx import pytest from sqlalchemy import select from sqlalchemy.ext.asyncio import AsyncSession from src.models.directories import RegionalOffice from tests.conftest import AuthClientFactory from tests.factories import make_company_group HTTP_OK = 200 HTTP_CREATED = 201 HTTP_NOT_FOUND = 404 HTTP_UNPROCESSABLE = 422 ROSTOV = "Ростовский региональный филиал" KRASNODAR = "Краснодарский региональный филиал" GROUPS = "/directories/company-groups" async def _office(session: AsyncSession, name: str) -> RegionalOffice: return (await session.execute(select(RegionalOffice).where(RegionalOffice.name == name))).scalar_one() @pytest.mark.integration async def test_branch_user_sees_only_own_groups(auth_client: AuthClientFactory, seeded: AsyncSession) -> None: rostov, krasnodar = await _office(seeded, ROSTOV), await _office(seeded, KRASNODAR) group_a = await make_company_group(seeded, name="ГК А", office=rostov) group_b = await make_company_group(seeded, name="ГК Б", office=krasnodar) branch = await auth_client("ka_rf@armka.local") # Ростовский филиал page = (await branch.get(GROUPS)).json() assert page["total"] == 1 assert [item["id"] for item in page["items"]] == [str(group_a.id)] head = await auth_client("ka_go@armka.local") ids = {item["id"] for item in (await head.get(GROUPS)).json()["items"]} assert {str(group_a.id), str(group_b.id)} <= ids @pytest.mark.integration async def test_foreign_group_is_indistinguishable_from_missing( auth_client: AuthClientFactory, seeded: AsyncSession ) -> None: krasnodar = await _office(seeded, KRASNODAR) group_b = await make_company_group(seeded, name="ГК Б", office=krasnodar) branch = await auth_client("ka_rf@armka.local") foreign = await branch.get(f"{GROUPS}/{group_b.id}") missing = await branch.get(f"{GROUPS}/{uuid.uuid4()}") assert foreign.status_code == missing.status_code == HTTP_NOT_FOUND assert foreign.json() == missing.json() # то же для остальных операций над чужой ГК for call in ( branch.patch(f"{GROUPS}/{group_b.id}", json={"name": "Взлом"}), branch.post(f"{GROUPS}/{group_b.id}/archive"), branch.post(f"{GROUPS}/{group_b.id}/unarchive"), branch.get(f"{GROUPS}/{group_b.id}/history"), ): response = await call assert response.status_code == HTTP_NOT_FOUND assert response.json() == missing.json() @pytest.mark.integration async def test_branch_user_creates_group_in_own_office_only( auth_client: AuthClientFactory, seeded: AsyncSession ) -> None: rostov, krasnodar = await _office(seeded, ROSTOV), await _office(seeded, KRASNODAR) branch: httpx.AsyncClient = await auth_client("ka_rf@armka.local") created = await branch.post(GROUPS, json={"name": "ГК Из филиала"}) assert created.status_code == HTTP_CREATED assert created.json()["base_regional_office_id"] == str(rostov.id) assert (await branch.get(f"{GROUPS}/{created.json()['id']}")).status_code == HTTP_OK # видна создателю foreign = await branch.post(GROUPS, json={"name": "ГК Чужая", "base_regional_office_id": str(krasnodar.id)}) assert foreign.status_code == HTTP_UNPROCESSABLE assert foreign.json()["detail"]["code"] == "OFFICE_NOT_ALLOWED"