From e2c5de703be45746bacaea4136f24440ff5a291c Mon Sep 17 00:00:00 2001 From: Max Nanis Date: Mon, 24 Aug 2026 12:35:35 -0700 Subject: Ruff std replacements --- tests/managers/gr/test_authentication.py | 3 --- 1 file changed, 3 deletions(-) (limited to 'tests/managers/gr/test_authentication.py') diff --git a/tests/managers/gr/test_authentication.py b/tests/managers/gr/test_authentication.py index 53b6931..b9f43a6 100644 --- a/tests/managers/gr/test_authentication.py +++ b/tests/managers/gr/test_authentication.py @@ -1,11 +1,9 @@ import logging -from random import randint from uuid import uuid4 import pytest from generalresearch.models.gr.authentication import GRUser -from test_utils.models.conftest import gr_user SSO_ISSUER = "" @@ -13,7 +11,6 @@ SSO_ISSUER = "" class TestGRUserManager: def test_create(self, gr_um): - from generalresearch.models.gr.authentication import GRUser user: GRUser = gr_um.create_dummy() instance = gr_um.get_by_id(user.id) -- cgit v1.2.3 From 97b14e2f133bda76f548ec1a522d9582c657d736 Mon Sep 17 00:00:00 2001 From: Max Nanis Date: Wed, 2 Sep 2026 16:51:06 -0700 Subject: managers/gr/test_auth is all green ✅ --- generalresearch/thl_django/app/test_settings.py | 2 +- test_utils/managers/upk/conftest.py | 8 +- test_utils/models/gr/conftest.py | 254 ++++++++++++++++-------- tests/managers/gr/test_authentication.py | 115 +++++++---- 4 files changed, 250 insertions(+), 129 deletions(-) (limited to 'tests/managers/gr/test_authentication.py') diff --git a/generalresearch/thl_django/app/test_settings.py b/generalresearch/thl_django/app/test_settings.py index c5df32a..2738aed 100644 --- a/generalresearch/thl_django/app/test_settings.py +++ b/generalresearch/thl_django/app/test_settings.py @@ -1,7 +1,7 @@ DATABASES = { "default": { "ENGINE": "django.db.backends.postgresql", - "NAME": 'unittest-2026-09-02-a0310b', + "NAME": 'unittest-2026-09-02-77ae16', "USER": 'jenkins', "PASSWORD": '123456789', "HOST": 'unittest-postgresql.fmt2.grl.internal', diff --git a/test_utils/managers/upk/conftest.py b/test_utils/managers/upk/conftest.py index f581278..23af1b3 100644 --- a/test_utils/managers/upk/conftest.py +++ b/test_utils/managers/upk/conftest.py @@ -13,11 +13,9 @@ from generalresearch.managers.thl.profiling.uqa import UQAManager from generalresearch.managers.thl.profiling.user_upk import ( UserUpkManager, ) - -if TYPE_CHECKING: - from generalresearch.models.thl.user import User - from generalresearch.pg_helper import PostgresConfig - from generalresearch.redis_helper import RedisConfig +from generalresearch.models.thl.user import User +from generalresearch.pg_helper import PostgresConfig +from generalresearch.redis_helper import RedisConfig @pytest.fixture(scope="session") diff --git a/test_utils/models/gr/conftest.py b/test_utils/models/gr/conftest.py index a73dd70..a5abf74 100644 --- a/test_utils/models/gr/conftest.py +++ b/test_utils/models/gr/conftest.py @@ -36,36 +36,6 @@ if TYPE_CHECKING: # --- Factory / Database --- -@pytest.fixture -def gr_user_factory(gr_user_manager: GRUserManager) -> Callable[..., GRUser]: - - def _inner( - sub: str | None = None, - is_superuser: bool = False, - ) -> GRUser: - sub = sub or f"{uuid4().hex}-{uuid4().hex}" - - return gr_user_manager.create( - sub=sub, - is_superuser=is_superuser, - ) - - return _inner - - -@pytest.fixture -def gr_user_cache( - gr_user: GRUser, - gr_db: PostgresConfig, - thl_web_rr: PostgresConfig, - gr_redis_config: RedisConfig, -) -> GRUser: - gr_user.set_cache( - pg_config=gr_db, thl_web_rr=thl_web_rr, redis_config=gr_redis_config - ) - return gr_user - - # --- Business Bank Account --- @@ -98,7 +68,7 @@ def gr_business_bank_account_factory( **kwargs, ) else: - raise ValueError("BusinessBankAccount Business not supported yet") + raise ValueError("Unsaved BusinessBankAccount not supported yet") return _inner @@ -115,16 +85,17 @@ def unsaved_gr_business_bank_account( return gr_business_factory(save=False) -# ----------------- +# --- Business Address --- @pytest.fixture def gr_business_address_factory( - gr_bam: BusinessAddressManager, + gr_business_address_manager: BusinessAddressManager, ) -> Callable[..., BusinessAddress]: def _inner( business_id: PositiveInt, + save: bool = True, uuid: UUIDStr | None = None, line_1: str | None = None, line_2: str | None = None, @@ -133,7 +104,7 @@ def gr_business_address_factory( postal_code: str | None = None, phone_number: PhoneNumber | None = None, country: str | None = None, - ): + ) -> BusinessAddress: uuid = uuid or uuid4().hex line_1 = line_1 or "abc" line_2 = line_2 or "bczx" @@ -143,21 +114,48 @@ def gr_business_address_factory( phone_number = None country = country or "US" - return gr_bam.create( - business_id=business_id, - uuid=uuid, - line_1=line_1, - line_2=line_2, - city=city, - state=state, - postal_code=postal_code, - phone_number=phone_number, - country=country, - ) + if save: + return gr_business_address_manager.create( + business_id=business_id, + uuid=uuid, + line_1=line_1, + line_2=line_2, + city=city, + state=state, + postal_code=postal_code, + phone_number=phone_number, + country=country, + ) + else: + raise ValueError("Unsaved BusinessAddress not supported yet") return _inner +# @pytest.fixture +# def business_address( +# gr_business: Business, business_address_manager: BusinessAddressManager +# ) -> : +# return business_address_manager.create_dummy(business_id=gr_business.id) + + +@pytest.fixture +def gr_business_address( + gr_business_address_factory: Callable[..., BusinessAddress], +) -> BusinessAddress: + return gr_business_address_factory(save=True) + + +@pytest.fixture +def unsaved_gr_business_address( + gr_business_address_factory: Callable[..., BusinessAddress], +) -> BusinessAddress: + return gr_business_address_factory(save=False) + + +# --- Business --- + + @pytest.fixture def gr_business_factory( gr_business_manager: BusinessManager, @@ -194,37 +192,127 @@ def unsaved_gr_business(gr_business_factory: Callable[..., Business]) -> Busines return gr_business_factory(save=False) +# --- GR Team --- + + @pytest.fixture -def gr_team( - gr_tm: TeamManager, +def gr_team_factory( + gr_team_manager: TeamManager, ) -> Callable[..., Team]: - def _inner(uuid: UUIDStr | None = None, name: str | None = None) -> Team: - uuid = uuid or uuid4().hex - name = name or f"name-{uuid4().hex[:12]}" + def _inner( + save: bool = True, + uuid: UUIDStr | None = None, + name: str | None = None, + **kwargs, + ) -> Team: + + if save: + return gr_team_manager.create(uuid=uuid, name=name, **kwargs) - return gr_tm.create(uuid=uuid, name=name) + else: + raise ValueError("BusinessBankAccount Business not supported yet") return _inner -@pytest.fixture() -def gr_user_token( - gr_user: GRUser, gr_tm: GRTokenManager, gr_db: PostgresConfig -) -> GRToken: - gr_tm.create(user_id=gr_user.id) - gr_user.prefetch_token(pg_config=gr_db) +@pytest.fixture +def gr_team(gr_team_factory: Callable[..., Team]) -> Team: + return gr_team_factory(save=True) + + +@pytest.fixture +def unsaved_gr_team( + gr_team_factory: Callable[..., Team], +) -> Team: + return gr_team_factory(save=False) - res = gr_user.token - assert res is not None, "GRToken should exist after creation and prefetching" - return res + +# --- GR User --- @pytest.fixture -def business_address( - gr_business: Business, business_address_manager: BusinessAddressManager -) -> BusinessAddress: - return business_address_manager.create_dummy(business_id=gr_business.id) +def gr_user_factory(gr_user_manager: GRUserManager) -> Callable[..., GRUser]: + + def _inner( + save: bool = True, + sub: str | None = None, + is_superuser: bool = False, + ) -> GRUser: + sub = sub or f"{uuid4().hex}-{uuid4().hex}" + + if save: + return gr_user_manager.create( + sub=sub, + is_superuser=is_superuser, + ) + else: + raise ValueError("Unsaved GR User not supported yet") + + return _inner + + +@pytest.fixture +def gr_user_cache( + gr_user: GRUser, + gr_db: PostgresConfig, + thl_web_rr: PostgresConfig, + gr_redis_config: RedisConfig, +) -> GRUser: + gr_user.set_cache( + pg_config=gr_db, thl_web_rr=thl_web_rr, redis_config=gr_redis_config + ) + return gr_user + + +@pytest.fixture +def gr_user(gr_user_factory: Callable[..., GRUser]) -> GRUser: + return gr_user_factory(save=True) + + +@pytest.fixture +def unsaved_gr_user( + gr_user_factory: Callable[..., GRUser], +) -> GRUser: + return gr_user_factory(save=False) + + +# --- GR User Token --- + + +@pytest.fixture +def gr_user_token_factory( + gr_user: GRUser, gr_user_token_manager: GRUser, gr_db: PostgresConfig +) -> Callable[..., GRToken]: + + def _inner( + save: bool = True, + ) -> GRToken: + + if save: + gr_user_token_manager.create(user_id=gr_user.id) + gr_user.prefetch_token(pg_config=gr_db) + + res = gr_user.token + assert ( + res is not None + ), "GRToken should exist after creation and prefetching" + return res + + else: + raise ValueError("Unsaved GR User not supported yet") + + return _inner + + +@pytest.fixture +def gr_user_token(gr_user_token_factory: Callable[..., GRToken]) -> GRToken: + return gr_user_token_factory(save=True) + + +@pytest.fixture +def unsaved_gr_user_token(gr_user_token_factory: Callable[..., GRToken]) -> GRToken: + return gr_user_token_factory(save=False) @pytest.fixture() @@ -232,26 +320,32 @@ def gr_user_token_header(gr_user_token: GRToken) -> dict[str, str]: return gr_user_token.auth_header -@pytest.fixture(scope="function") -def membership(team: Team, gr_user: GRUser, team_manager: TeamManager) -> Membership: - assert team.id, "Team must be saved" - assert gr_user.id, "GRUser must be saved" - return team_manager.add_user(team=team, gr_user=gr_user) +# --- GR Membership --- -@pytest.fixture(scope="function") -def membership_factory( - team: Team, +@pytest.fixture() +def gr_membership_factory( + gr_team: Team, gr_user: GRUser, - membership_manager: MembershipManager, - team_manager: TeamManager, - gr_um: GRUserManager, + gr_membership_manager: MembershipManager, ) -> Callable[..., Membership]: - def _inner(**kwargs) -> Membership: - _team = kwargs.get("team", team_manager.create_dummy()) - _gr_user = kwargs.get("gr_user", gr_um.create_dummy()) - - return membership_manager.create(team=_team, gr_user=_gr_user) + def _inner(save: bool = True, **kwargs) -> Membership: + if save: + return gr_membership_manager.create(team=gr_team, gr_user=gr_user, **kwargs) + else: + raise ValueError("Unsaved GR Membership not supported yet") return _inner + + +@pytest.fixture() +def gr_membership(gr_membership_factory: Callable[..., Membership]) -> Membership: + return gr_membership_factory(save=True) + + +@pytest.fixture() +def unsaved_gr_membership( + gr_membership_factory: Callable[..., Membership], +) -> Membership: + return gr_membership_factory(save=False) diff --git a/tests/managers/gr/test_authentication.py b/tests/managers/gr/test_authentication.py index b9f43a6..0bcabc5 100644 --- a/tests/managers/gr/test_authentication.py +++ b/tests/managers/gr/test_authentication.py @@ -1,117 +1,146 @@ import logging +from collections.abc import Callable from uuid import uuid4 import pytest -from generalresearch.models.gr.authentication import GRUser +from generalresearch.managers.gr.authentication import GRTokenManager, GRUserManager +from generalresearch.managers.gr.team import TeamManager +from generalresearch.models.gr.authentication import GRToken, GRUser +from generalresearch.pg_helper import PostgresConfig +from generalresearch.redis_helper import RedisConfig SSO_ISSUER = "" class TestGRUserManager: - def test_create(self, gr_um): - - user: GRUser = gr_um.create_dummy() - instance = gr_um.get_by_id(user.id) - assert user.id == instance.id + def test_create(self, gr_user: GRUser, gr_user_manager: GRUserManager): + instance = gr_user_manager.get_by_id(gr_user.id) + assert isinstance(instance, GRUser) + assert gr_user.id == instance.id - instance2 = gr_um.get_by_id(user.id) - assert user.model_dump_json() == instance2.model_dump_json() + instance2 = gr_user_manager.get_by_id(gr_user.id) + assert isinstance(instance2, GRUser) + assert gr_user.model_dump_json() == instance2.model_dump_json() - def test_get_by_id(self, gr_user, gr_um): + def test_get_by_id(self, gr_user: GRUser, gr_user_manager: GRUserManager): with pytest.raises(expected_exception=ValueError) as cm: - gr_um.get_by_id(gr_user_id=999_999_999) + gr_user_manager.get_by_id(gr_user_id=999_999_999) assert "GRUser not found" in str(cm.value) - instance = gr_um.get_by_id(gr_user_id=gr_user.id) + instance = gr_user_manager.get_by_id(gr_user_id=gr_user.id) + assert isinstance(instance, GRUser) assert instance.sub == gr_user.sub - def test_get_by_sub(self, gr_user, gr_um): + def test_get_by_sub(self, gr_user: GRUser, gr_user_manager: GRUserManager): with pytest.raises(expected_exception=ValueError) as cm: - gr_um.get_by_sub(sub=uuid4().hex) + gr_user_manager.get_by_sub(sub=uuid4().hex) assert "GRUser not found" in str(cm.value) - instance = gr_um.get_by_sub(sub=gr_user.sub) + instance = gr_user_manager.get_by_sub(sub=gr_user.sub) + assert isinstance(instance, GRUser) assert instance.id == gr_user.id - def test_get_by_sub_or_create(self, gr_user, gr_um): + def test_get_by_sub_or_create( + self, gr_user: GRUser, gr_user_manager: GRUserManager + ): sub = f"{uuid4().hex}-{uuid4().hex}" with pytest.raises(expected_exception=ValueError) as cm: - gr_um.get_by_sub(sub=sub) + gr_user_manager.get_by_sub(sub=sub) assert "GRUser not found" in str(cm.value) - instance = gr_um.get_by_sub_or_create(sub=sub) + instance = gr_user_manager.get_by_sub_or_create(sub=sub) assert isinstance(instance, GRUser) assert instance.sub == sub - def test_get_all(self, gr_um): - res1 = gr_um.get_all() + def test_get_all( + self, gr_user_factory: Callable[..., GRUser], gr_user_manager: GRUserManager + ): + res1 = gr_user_manager.get_all() assert isinstance(res1, list) - gr_um.create_dummy() - res2 = gr_um.get_all() + gr_user_factory(save=True) + res2 = gr_user_manager.get_all() assert len(res1) == len(res2) - 1 - def test_get_by_team(self, gr_um): - res = gr_um.get_by_team(team_id=999_999_999) + def test_get_by_team(self, gr_user_manager: GRUserManager): + res = gr_user_manager.get_by_team(team_id=999_999_999) assert isinstance(res, list) assert res == [] - def test_list_product_uuids(self, caplog, gr_user, gr_um, thl_web_rr): + def test_list_product_uuids( + self, + caplog, + gr_user: GRUser, + gr_user_manager: GRUserManager, + thl_web_rr: PostgresConfig, + ): with caplog.at_level(logging.WARNING): - gr_um.list_product_uuids(user=gr_user, thl_pg_config=thl_web_rr) + gr_user_manager.list_product_uuids(user=gr_user, thl_pg_config=thl_web_rr) assert "prefetch not run" in caplog.text class TestGRTokenManager: - def test_create(self, gr_user, gr_tm): - assert gr_tm.create(user_id=gr_user.id) is None + def test_create(self, gr_user: GRUser, gr_team_manager: TeamManager): + assert gr_team_manager.create(user_id=gr_user.id) is None - token = gr_tm.get_by_user_id(user_id=gr_user.id) + token = gr_team_manager.get_by_user_id(user_id=gr_user.id) assert gr_user.id == token.user_id - def test_get_by_user_id(self, gr_user, gr_tm): - assert gr_tm.create(user_id=gr_user.id) is None + def test_get_by_user_id(self, gr_user: GRUser, gr_team_manager: TeamManager): + assert gr_team_manager.create(user_id=gr_user.id) is None - token = gr_tm.get_by_user_id(user_id=gr_user.id) + token = gr_team_manager.get_by_user_id(user_id=gr_user.id) assert gr_user.id == token.user_id - def test_prefetch_user(self, gr_user, gr_tm, gr_db, gr_redis_config): - from generalresearch.models.gr.authentication import GRToken + def test_prefetch_user( + self, + gr_user: GRUser, + gr_team_manager: TeamManager, + gr_db: PostgresConfig, + gr_redis_config: RedisConfig, + ): - gr_tm.create(user_id=gr_user.id) + gr_team_manager.create(user_id=gr_user.id) - token: GRToken = gr_tm.get_by_user_id(user_id=gr_user.id) + token: GRToken = gr_team_manager.get_by_user_id(user_id=gr_user.id) assert token.user is None token.prefetch_user(pg_config=gr_db, redis_config=gr_redis_config) assert token.user.id == gr_user.id - def test_get_by_key(self, gr_user, gr_um, gr_tm): - gr_tm.create(user_id=gr_user.id) - token = gr_tm.get_by_user_id(user_id=gr_user.id) + def test_get_by_key( + self, + gr_user: GRUser, + gr_team_manager: TeamManager, + ): + gr_team_manager.create(user_id=gr_user.id) + token = gr_team_manager.get_by_user_id(user_id=gr_user.id) - instance = gr_tm.get_by_key(api_key=token.key) + instance = gr_team_manager.get_by_key(api_key=token.key) assert token.created == instance.created # Search for non-existent key with pytest.raises(expected_exception=Exception) as cm: - gr_tm.get_by_key(api_key=uuid4().hex) + gr_team_manager.get_by_key(api_key=uuid4().hex) assert "No GRUser with token of " in str(cm.value) @pytest.mark.skip(reason="no idea how to actually test this...") - def test_get_by_sso_key(self, gr_user, gr_um, gr_tm, gr_redis_config): - from generalresearch.models.gr.authentication import GRToken + def test_get_by_sso_key( + self, + gr_team_manager: TeamManager, + gr_redis_config: RedisConfig, + ): api_key = "..." jwks = { # ... } - instance = gr_tm.get_by_key( + instance = gr_team_manager.get_by_key( api_key=api_key, jwks=jwks, audience="...", -- cgit v1.2.3 From ad620d7586640534a092672b8f3cddf6eff5604b Mon Sep 17 00:00:00 2001 From: Max Nanis Date: Wed, 2 Sep 2026 17:40:18 -0700 Subject: gr mangers all green ✅ --- Jenkinsfile | 16 +++++ generalresearch/managers/gr/team.py | 7 +- generalresearch/models/thl/product.py | 4 +- generalresearch/thl_django/app/test_settings.py | 2 +- test_utils/managers/gr/conftest.py | 22 +++++- test_utils/models/conftest.py | 31 +-------- test_utils/models/gr/conftest.py | 10 +-- test_utils/models/thl/conftest.py | 61 +++++++++++------ tests/managers/gr/test_authentication.py | 32 +++++---- tests/managers/gr/test_business.py | 22 ++++-- tests/managers/gr/test_team.py | 91 +++++++++++++++---------- 11 files changed, 180 insertions(+), 118 deletions(-) (limited to 'tests/managers/gr/test_authentication.py') diff --git a/Jenkinsfile b/Jenkinsfile index de909b2..a646d22 100644 --- a/Jenkinsfile +++ b/Jenkinsfile @@ -60,6 +60,14 @@ pipeline { } stage('base') { + steps { + dir("generalresearch-${VER}") { + sh "${VENV}-${VER}/bin/pytest tests/test_postgres.py -vs" + } + } + } + + stage('models') { steps { dir("generalresearch-${VER}") { sh "${VENV}-${VER}/bin/pytest tests/models/gr/test_base.py -vs" @@ -67,6 +75,14 @@ pipeline { } } + stage('managers') { + steps { + dir("generalresearch-${VER}") { + sh "${VENV}-${VER}/bin/pytest tests/managers/gr/ -vs" + } + } + } + } } } diff --git a/generalresearch/managers/gr/team.py b/generalresearch/managers/gr/team.py index e551f85..41af709 100644 --- a/generalresearch/managers/gr/team.py +++ b/generalresearch/managers/gr/team.py @@ -11,6 +11,7 @@ from generalresearch.managers.base import ( PostgresManager, PostgresManagerWithRedis, ) +from generalresearch.managers.gr.authentication import GRUserManager from generalresearch.models.custom_types import UUIDStr from generalresearch.models.gr.team import ( Membership, @@ -187,10 +188,12 @@ class TeamManager(PostgresManagerWithRedis): return team - def add_user(self, team: Team, gr_user: GRUser) -> Membership: + def add_user( + self, team: Team, gr_user: GRUser, gr_user_manager: GRUserManager + ) -> Membership: """Create a Membership between a GRUser and a Team""" - team.prefetch_gr_users(pg_config=self.pg_config, redis_config=self.redis_config) + team.prefetch_gr_users(gr_user_manager=gr_user_manager) assert gr_user not in team.gr_users, ( "Can't create multiple Memberships for " "the same User to the same Team" diff --git a/generalresearch/models/thl/product.py b/generalresearch/models/thl/product.py index 346a98b..3677ff2 100644 --- a/generalresearch/models/thl/product.py +++ b/generalresearch/models/thl/product.py @@ -1396,8 +1396,8 @@ class Product(BaseModel, validate_assignment=True): # --- ORM --- - def model_dump_mysql(self) -> dict[str, Any]: - d = self.model_dump(mode="json") + def model_dump_mysql(self, *args, **kwargs) -> dict[str, Any]: + d = self.model_dump(mode="json", *args, **kwargs) assert self.created if "created" in d: diff --git a/generalresearch/thl_django/app/test_settings.py b/generalresearch/thl_django/app/test_settings.py index 2738aed..276b94a 100644 --- a/generalresearch/thl_django/app/test_settings.py +++ b/generalresearch/thl_django/app/test_settings.py @@ -1,7 +1,7 @@ DATABASES = { "default": { "ENGINE": "django.db.backends.postgresql", - "NAME": 'unittest-2026-09-02-77ae16', + "NAME": 'unittest-2026-09-03-ab1271', "USER": 'jenkins', "PASSWORD": '123456789', "HOST": 'unittest-postgresql.fmt2.grl.internal', diff --git a/test_utils/managers/gr/conftest.py b/test_utils/managers/gr/conftest.py index b5db2a5..cc1053c 100644 --- a/test_utils/managers/gr/conftest.py +++ b/test_utils/managers/gr/conftest.py @@ -7,7 +7,6 @@ from typing import TYPE_CHECKING import pytest import redis -import redis.asyncio as redis_async from pydantic import PostgresDsn from generalresearch.managers.gr.business import ( @@ -15,12 +14,14 @@ from generalresearch.managers.gr.business import ( BusinessBankAccountManager, BusinessManager, ) +from generalresearch.managers.gr.team import MembershipManager from generalresearch.pg_helper import PostgresConfig from generalresearch.redis_helper import RedisConfig if TYPE_CHECKING: from generalresearch.config import GRLBaseSettings from generalresearch.managers.gr.authentication import GRTokenManager, GRUserManager + from generalresearch.managers.gr.team import TeamManager # === Msc === @@ -89,7 +90,17 @@ def gr_user_manager( @pytest.fixture(scope="session") -def gr_team_manager(gr_db: PostgresConfig) -> GRTokenManager: +def gr_team_manager(gr_db: PostgresConfig, gr_redis_config: RedisConfig) -> TeamManager: + assert gr_db.dsn.path + assert "/unittest-" in gr_db.dsn.path + + from generalresearch.managers.gr.team import TeamManager + + return TeamManager(pg_config=gr_db, redis_config=gr_redis_config) + + +@pytest.fixture(scope="session") +def gr_token_manager(gr_db: PostgresConfig) -> GRTokenManager: assert gr_db.dsn.path assert "/unittest-" in gr_db.dsn.path @@ -117,3 +128,10 @@ def gr_business_address_manager( gr_db: PostgresConfig, ) -> BusinessAddressManager: return BusinessAddressManager(pg_config=gr_db) + + +@pytest.fixture(scope="session") +def gr_membership_manager( + gr_db: PostgresConfig, +) -> MembershipManager: + return MembershipManager(pg_config=gr_db) diff --git a/test_utils/models/conftest.py b/test_utils/models/conftest.py index ed4da08..d71593f 100644 --- a/test_utils/models/conftest.py +++ b/test_utils/models/conftest.py @@ -286,36 +286,7 @@ def session( return session -@pytest.fixture -def product(request: Request, product_manager: ProductManager) -> Product: - - team = getattr(request, "team", None) - business = getattr(request, "business", None) - - return product_manager.create_dummy( - team_id=team.uuid if team else None, - business_id=business.uuid if business else None, - ) - - -@pytest.fixture -def product_factory(product_manager: ProductManager) -> Callable[..., Product]: - - def _inner( - team: Team | None = None, - business: Business | None = None, - commission_pct: Decimal = Decimal("0.05"), - ) -> Product: - return product_manager.create_dummy( - team_id=team.uuid if team else None, - business_id=business.uuid if business else None, - commission_pct=commission_pct, - ) - - return _inner - - -@pytest.fixture +@pytest.fixture() def payout_config(request: Request) -> PayoutConfig: from generalresearch.models.thl.product import ( PayoutConfig, diff --git a/test_utils/models/gr/conftest.py b/test_utils/models/gr/conftest.py index a5abf74..3dd73a1 100644 --- a/test_utils/models/gr/conftest.py +++ b/test_utils/models/gr/conftest.py @@ -207,8 +207,10 @@ def gr_team_factory( **kwargs, ) -> Team: + name = name or f"" + if save: - return gr_team_manager.create(uuid=uuid, name=name, **kwargs) + return gr_team_manager.create(name=name, uuid=uuid, **kwargs) else: raise ValueError("BusinessBankAccount Business not supported yet") @@ -325,12 +327,12 @@ def gr_user_token_header(gr_user_token: GRToken) -> dict[str, str]: @pytest.fixture() def gr_membership_factory( - gr_team: Team, - gr_user: GRUser, gr_membership_manager: MembershipManager, ) -> Callable[..., Membership]: - def _inner(save: bool = True, **kwargs) -> Membership: + def _inner( + gr_team: Team, gr_user: GRUser, save: bool = True, **kwargs + ) -> Membership: if save: return gr_membership_manager.create(team=gr_team, gr_user=gr_user, **kwargs) else: diff --git a/test_utils/models/thl/conftest.py b/test_utils/models/thl/conftest.py index 3545509..badd87c 100644 --- a/test_utils/models/thl/conftest.py +++ b/test_utils/models/thl/conftest.py @@ -39,6 +39,7 @@ if TYPE_CHECKING: from generalresearch.managers.thl.userhealth import AuditLogManager, IPRecordManager from generalresearch.managers.thl.wall import WallManager from generalresearch.models.definitions import DeviceType + from generalresearch.models.gr.team import Team from generalresearch.models.legacy.bucket import Bucket from generalresearch.models.thl.ipinfo import IPGeoname, IPInformation from generalresearch.models.thl.payout import UserPayoutEvent @@ -144,12 +145,18 @@ def wall_factory( return _inner -@pytest.fixture +# --- Product --- + + +@pytest.fixture() def product_factory(product_manager: ProductManager) -> Callable[..., Product]: def _inner( + save: bool = True, + team: Team | None = None, + # business: Business | None = None, + # commission_pct: Decimal = Decimal("0.05"), product_id: UUIDStr | None = None, - team_id: UUIDStr | None = None, business_id: UUIDStr | None = None, name: str | None = None, redirect_url: str | None = None, @@ -165,30 +172,46 @@ def product_factory(product_manager: ProductManager) -> Callable[..., Product]: ) -> Product: """To be used in tests, where we don't care about certain fields""" product_id = product_id if product_id else uuid4().hex - team_id = team_id if team_id else uuid4().hex + team_id = team.uuid if team else uuid4().hex name = name if name else f"name-{product_id[:12]}" redirect_url = redirect_url if redirect_url else "https://www.example.com/" - return product_manager.create( - product_id=product_id, - team_id=team_id, - business_id=business_id, - name=name, - redirect_url=redirect_url, - harmonizer_domain=harmonizer_domain, - commission_pct=commission_pct, - sources_config=sources_config, - payout_config=payout_config, - session_config=session_config, - profiling_config=profiling_config, - user_wallet_config=user_wallet_config, - user_create_config=user_create_config, - user_health_config=user_health_config, - ) + if save: + return product_manager.create( + product_id=product_id, + team_id=team_id, + business_id=business_id, + name=name, + redirect_url=redirect_url, + harmonizer_domain=harmonizer_domain, + commission_pct=commission_pct, + sources_config=sources_config, + payout_config=payout_config, + session_config=session_config, + profiling_config=profiling_config, + user_wallet_config=user_wallet_config, + user_create_config=user_create_config, + user_health_config=user_health_config, + ) + else: + raise ValueError("Unsaved Product not yet supported") return _inner +@pytest.fixture() +def product(product_factory: Callable[..., Product]) -> Product: + return product_factory(save=True) + + +@pytest.fixture() +def unsaved_product(product_factory: Callable[..., Product]) -> Product: + return product_factory(save=False) + + +# --- Session --- + + @pytest.fixture def session_factory(session_manager: SessionManager): diff --git a/tests/managers/gr/test_authentication.py b/tests/managers/gr/test_authentication.py index 0bcabc5..1310c79 100644 --- a/tests/managers/gr/test_authentication.py +++ b/tests/managers/gr/test_authentication.py @@ -84,29 +84,32 @@ class TestGRUserManager: class TestGRTokenManager: - def test_create(self, gr_user: GRUser, gr_team_manager: TeamManager): - assert gr_team_manager.create(user_id=gr_user.id) is None + def test_create(self, gr_user: GRUser, gr_token_manager: GRTokenManager): + assert gr_token_manager.create(user_id=gr_user.id) is None - token = gr_team_manager.get_by_user_id(user_id=gr_user.id) + token = gr_token_manager.get_by_user_id(user_id=gr_user.id) + assert isinstance(token, GRToken) assert gr_user.id == token.user_id - def test_get_by_user_id(self, gr_user: GRUser, gr_team_manager: TeamManager): - assert gr_team_manager.create(user_id=gr_user.id) is None + def test_get_by_user_id(self, gr_user: GRUser, gr_token_manager: GRTokenManager): + assert gr_token_manager.create(user_id=gr_user.id) is None - token = gr_team_manager.get_by_user_id(user_id=gr_user.id) + token = gr_token_manager.get_by_user_id(user_id=gr_user.id) + assert isinstance(token, GRToken) assert gr_user.id == token.user_id def test_prefetch_user( self, gr_user: GRUser, - gr_team_manager: TeamManager, + gr_token_manager: GRTokenManager, gr_db: PostgresConfig, gr_redis_config: RedisConfig, ): - gr_team_manager.create(user_id=gr_user.id) + gr_token_manager.create(user_id=gr_user.id) - token: GRToken = gr_team_manager.get_by_user_id(user_id=gr_user.id) + token: GRToken | None = gr_token_manager.get_by_user_id(user_id=gr_user.id) + assert isinstance(token, GRToken) assert token.user is None token.prefetch_user(pg_config=gr_db, redis_config=gr_redis_config) @@ -115,17 +118,18 @@ class TestGRTokenManager: def test_get_by_key( self, gr_user: GRUser, - gr_team_manager: TeamManager, + gr_token_manager: GRTokenManager, ): - gr_team_manager.create(user_id=gr_user.id) - token = gr_team_manager.get_by_user_id(user_id=gr_user.id) + gr_token_manager.create(user_id=gr_user.id) + token = gr_token_manager.get_by_user_id(user_id=gr_user.id) + assert isinstance(token, GRToken) - instance = gr_team_manager.get_by_key(api_key=token.key) + instance = gr_token_manager.get_by_key(api_key=token.key) assert token.created == instance.created # Search for non-existent key with pytest.raises(expected_exception=Exception) as cm: - gr_team_manager.get_by_key(api_key=uuid4().hex) + gr_token_manager.get_by_key(api_key=uuid4().hex) assert "No GRUser with token of " in str(cm.value) @pytest.mark.skip(reason="no idea how to actually test this...") diff --git a/tests/managers/gr/test_business.py b/tests/managers/gr/test_business.py index 3513af5..0d5b0d5 100644 --- a/tests/managers/gr/test_business.py +++ b/tests/managers/gr/test_business.py @@ -1,3 +1,4 @@ +from collections.abc import Callable from typing import TYPE_CHECKING from uuid import uuid4 @@ -9,6 +10,7 @@ from generalresearch.models.gr.business import ( BusinessBankAccount, ) from generalresearch.models.gr.definitions import TransferMethod +from generalresearch.models.gr.team import Team if TYPE_CHECKING: from generalresearch.managers.gr.business import ( @@ -68,9 +70,9 @@ class TestBusinessAddressManager: class TestBusinessManager: - def test_create(self, business_manager: BusinessManager): + def test_create(self, gr_business_factory: Callable[..., Business]): - instance = business_manager.create_dummy() + instance = gr_business_factory() assert isinstance(instance, Business) assert isinstance(instance.id, int) @@ -88,11 +90,15 @@ class TestBusinessManager: assert isinstance(res, Business) assert res.id == instance.id - def test_get_all(self, business_manager: BusinessManager): + def test_get_all( + self, + business_manager: BusinessManager, + gr_business_factory: Callable[..., Business], + ): res1 = business_manager.get_all() assert isinstance(res1, list) - business_manager.create_dummy() + gr_business_factory() res2 = business_manager.get_all() assert len(res1) == len(res2) - 1 @@ -106,17 +112,19 @@ class TestBusinessManager: gr_user: GRUser, team_manager: TeamManager, membership_manager: MembershipManager, + gr_business_factory: Callable[..., Business], + gr_team_factory: Callable[..., Team], ): res = business_manager.get_by_user_id(user_id=gr_user.id) assert len(res) == 0 # Create a business: Business, but don't add it to anything - b1 = business_manager.create_dummy() + b1 = gr_business_factory() res = business_manager.get_by_user_id(user_id=gr_user.id) assert len(res) == 0 # Create a Team, but don't create any Memberships - t1 = team_manager.create_dummy() + t1 = gr_team_factory() res = business_manager.get_by_user_id(user_id=gr_user.id) assert len(res) == 0 @@ -133,7 +141,7 @@ class TestBusinessManager: assert len(res) == 1 # Add another Business to the Team! - b2 = business_manager.create_dummy() + b2 = gr_business_factory() team_manager.add_business(team=t1, business=b2) res = business_manager.get_by_user_id(user_id=gr_user.id) assert len(res) == 2 diff --git a/tests/managers/gr/test_team.py b/tests/managers/gr/test_team.py index 17e0470..751e33c 100644 --- a/tests/managers/gr/test_team.py +++ b/tests/managers/gr/test_team.py @@ -4,6 +4,7 @@ from collections.abc import Callable from typing import TYPE_CHECKING from uuid import uuid4 +from generalresearch.models.gr.authentication import GRUser from generalresearch.models.gr.team import Membership, Team if TYPE_CHECKING: @@ -23,94 +24,110 @@ class TestMembershipManager: class TestTeamManager: - def test_init(self, team_manager: TeamManager, gr_db: PostgresConfig): - assert team_manager.pg_config == gr_db + def test_init(self, gr_team_manager: TeamManager, gr_db: PostgresConfig): + assert gr_team_manager.pg_config == gr_db - def test_get_or_create(self, team_manager: TeamManager): + def test_get_or_create(self, gr_team_manager: TeamManager): from generalresearch.models.gr.team import Team new_uuid = uuid4().hex - team: Team = team_manager.get_or_create(uuid=new_uuid) + team: Team = gr_team_manager.get_or_create(uuid=new_uuid) assert isinstance(team, Team) assert isinstance(team.id, int) assert team.uuid == new_uuid assert team.name == "< Unknown >" - def test_get_all(self, team_manager: TeamManager): - res1 = team_manager.get_all() + def test_get_all( + self, gr_team_factory: Callable[..., Team], gr_team_manager: TeamManager + ): + res1 = gr_team_manager.get_all() assert isinstance(res1, list) - team_manager.create_dummy() - res2 = team_manager.get_all() + gr_team_factory() + res2 = gr_team_manager.get_all() assert len(res1) == len(res2) - 1 - def test_create(self, team_manager: TeamManager): + def test_create( + self, gr_team_factory: Callable[..., Team], gr_team_manager: TeamManager + ): - team: Team = team_manager.create_dummy() + team: Team = gr_team_factory() assert isinstance(team, Team) assert isinstance(team.id, int) def test_add_user( self, - team: Team, - team_manager: TeamManager, - gr_um: GRUserManager, - gr_db: PostgresConfig, - gr_redis_config: RedisConfig, + gr_team: Team, + gr_team_manager: TeamManager, + gr_user_manager: GRUserManager, + gr_user_factory: Callable[..., GRUser], ): - user: GRUser = gr_um.create_dummy() + user: GRUser = gr_user_factory() - instance = team_manager.add_user(team=team, gr_user=user) + instance = gr_team_manager.add_user( + gr_user_manager=gr_user_manager, team=gr_team, gr_user=user + ) assert isinstance(instance, Membership) # assert team.gr_users is None - team.prefetch_gr_users(pg_config=gr_db, redis_config=gr_redis_config) - assert isinstance(team.gr_users, list) - assert len(team.gr_users) - assert team.gr_users == [user] + gr_team.prefetch_gr_users(gr_user_manager=gr_user_manager) + assert isinstance(gr_team.gr_users, list) + assert len(gr_team.gr_users) + assert gr_team.gr_users == [user] - def test_get_by_uuid(self, team_manager: TeamManager): + def test_get_by_uuid( + self, gr_team_factory: Callable[..., Team], gr_team_manager: TeamManager + ): - team: Team = team_manager.create_dummy() + team: Team = gr_team_factory() - instance = team_manager.get_by_uuid(team_uuid=team.uuid) + instance = gr_team_manager.get_by_uuid(team_uuid=team.uuid) + assert isinstance(instance, Team) assert team.id == instance.id - def test_get_by_id(self, team_manager: TeamManager): + def test_get_by_id( + self, gr_team_factory: Callable[..., Team], gr_team_manager: TeamManager + ): - team: Team = team_manager.create_dummy() + team: Team = gr_team_factory() - instance = team_manager.get_by_id(team_id=team.id) + instance = gr_team_manager.get_by_id(team_id=team.id) + assert isinstance(instance, Team) assert team.uuid == instance.uuid def test_get_by_user( - self, team: Team, team_manager: TeamManager, gr_um: GRUserManager + self, + gr_team: Team, + gr_user_factory: Callable[..., GRUser], + gr_team_manager: TeamManager, + gr_user_manager: GRUserManager, ): + user: GRUser = gr_user_factory() + gr_team_manager.add_user( + gr_user_manager=gr_user_manager, team=gr_team, gr_user=user + ) - user: GRUser = gr_um.create_dummy() - team_manager.add_user(team=team, gr_user=user) - - res = team_manager.get_by_user(gr_user=user) + res = gr_team_manager.get_by_user(gr_user=user) assert isinstance(res, list) assert len(res) == 1 instance = res[0] assert isinstance(instance, Team) - assert instance.uuid == team.uuid + assert instance.uuid == gr_team.uuid def test_get_by_user_duplicates( self, gr_user: GRUser, product_factory: Callable[..., Product], - membership_factory: Callable[..., Membership], - team: Team, + gr_membership_factory: Callable[..., Membership], + gr_team: Team, gr_redis_config: RedisConfig, gr_db: PostgresConfig, ): - product_factory(team=team) - membership_factory(team=team, gr_user=gr_user) + product_factory(team=gr_team) + gr_membership_factory(gr_team=gr_team, gr_user=gr_user) gr_user.prefetch_teams( pg_config=gr_db, -- cgit v1.2.3