All checks were successful
Deploy Development / deploy (push) Successful in 40s
Test Suite / pytest-backend (push) Successful in 25s
Test Suite / lint-backend (push) Successful in 0s
Test Suite / build-frontend (push) Successful in 7s
Test Suite / playwright-tests (push) Successful in 23s
- Introduced a new utility function to filter and return only active club memberships, improving role management and access control. - Updated various components and pages to utilize the new active club memberships function, ensuring only relevant memberships are considered. - Enhanced user interface elements to reflect the status of club memberships, including visual indicators for inactive memberships. - Improved backend logic for resolving tenant contexts and managing club roles based on active memberships.
162 lines
4.6 KiB
Python
162 lines
4.6 KiB
Python
"""Unit tests ohne Datenbank für die Zugriffsschicht (Visibility-SQL, Header-Parsing)."""
|
|
import pytest
|
|
from fastapi import HTTPException
|
|
|
|
from tenant_context import library_content_visibility_sql, parse_active_club_header, resolve_tenant_context
|
|
|
|
|
|
def test_library_visibility_sql_platform_admin_no_filter():
|
|
sql, params = library_content_visibility_sql(
|
|
alias="e",
|
|
profile_id=1,
|
|
role="admin",
|
|
effective_club_id=None,
|
|
)
|
|
assert sql == "TRUE"
|
|
assert params == []
|
|
|
|
|
|
def test_library_visibility_sql_superadmin():
|
|
sql, params = library_content_visibility_sql(
|
|
alias="fp",
|
|
profile_id=2,
|
|
role="superadmin",
|
|
effective_club_id=100,
|
|
)
|
|
assert sql == "TRUE"
|
|
assert params == []
|
|
|
|
|
|
def test_library_visibility_sql_trainer_without_active_club_no_shared_club_branch():
|
|
sql, params = library_content_visibility_sql(
|
|
alias="g",
|
|
profile_id=42,
|
|
role="trainer",
|
|
effective_club_id=None,
|
|
)
|
|
assert "official" in sql
|
|
assert "private" in sql
|
|
assert "visibility = 'club'" not in sql
|
|
assert params == [42]
|
|
|
|
|
|
def test_library_visibility_sql_user_with_active_club_includes_club_branch():
|
|
sql, params = library_content_visibility_sql(
|
|
alias="t",
|
|
profile_id=7,
|
|
role="user",
|
|
effective_club_id=99,
|
|
)
|
|
assert "visibility = 'club'" in sql
|
|
assert "club_members" in sql
|
|
assert params[0] == 7 # private branch created_by
|
|
assert 99 in params
|
|
assert params.count(7) >= 2 # private + EXISTS membership
|
|
|
|
|
|
def test_parse_active_club_header_none_and_empty():
|
|
assert parse_active_club_header(None) is None
|
|
assert parse_active_club_header("") is None
|
|
assert parse_active_club_header(" ") is None
|
|
|
|
|
|
def test_parse_active_club_header_valid():
|
|
assert parse_active_club_header("12") == 12
|
|
|
|
|
|
def test_parse_active_club_header_invalid():
|
|
with pytest.raises(HTTPException) as exc:
|
|
parse_active_club_header("not-int")
|
|
assert exc.value.status_code == 400
|
|
|
|
|
|
def test_parse_active_club_header_non_positive():
|
|
with pytest.raises(HTTPException) as exc:
|
|
parse_active_club_header("0")
|
|
assert exc.value.status_code == 400
|
|
|
|
|
|
def test_resolve_platform_admin_uses_stored_club_without_header(monkeypatch):
|
|
"""Ohne X-Active-Club-Id: effective wie gespeichertes Profil (Sync mit Dropdown/DB)."""
|
|
cur = object()
|
|
|
|
def fake_exists(c, cid):
|
|
return cid == 99
|
|
|
|
monkeypatch.setattr("tenant_context._club_exists", fake_exists)
|
|
ctx = resolve_tenant_context(
|
|
cur,
|
|
profile_id=1,
|
|
global_role="admin",
|
|
header_raw=None,
|
|
memberships=[{"id": 10}],
|
|
stored_active_club_id=99,
|
|
)
|
|
assert ctx.effective_club_id == 99
|
|
|
|
|
|
def test_resolve_platform_admin_header_overrides_stored(monkeypatch):
|
|
cur = object()
|
|
|
|
def fake_exists(c, cid):
|
|
return cid in (5, 99)
|
|
|
|
monkeypatch.setattr("tenant_context._club_exists", fake_exists)
|
|
ctx = resolve_tenant_context(
|
|
cur,
|
|
profile_id=1,
|
|
global_role="superadmin",
|
|
header_raw="5",
|
|
memberships=[{"id": 10}],
|
|
stored_active_club_id=99,
|
|
)
|
|
assert ctx.effective_club_id == 5
|
|
|
|
|
|
def test_resolve_platform_admin_no_header_stored_invalid(monkeypatch):
|
|
cur = object()
|
|
monkeypatch.setattr("tenant_context._club_exists", lambda c, cid: False)
|
|
ctx = resolve_tenant_context(
|
|
cur,
|
|
profile_id=1,
|
|
global_role="admin",
|
|
header_raw=None,
|
|
memberships=[{"id": 1}],
|
|
stored_active_club_id=123,
|
|
)
|
|
assert ctx.effective_club_id is None
|
|
|
|
|
|
def test_resolve_trainer_club_ids_excludes_inactive_memberships():
|
|
"""Nur aktive Vereinszugänge zählen für Mandant / Header-Validierung."""
|
|
cur = object()
|
|
ctx = resolve_tenant_context(
|
|
cur,
|
|
profile_id=9,
|
|
global_role="user",
|
|
header_raw=None,
|
|
memberships=[
|
|
{"id": 10, "membership_status": "inactive"},
|
|
{"id": 20, "membership_status": "active"},
|
|
],
|
|
stored_active_club_id=None,
|
|
invalid_header_policy="ignore",
|
|
)
|
|
assert ctx.club_ids == frozenset({20})
|
|
assert ctx.effective_club_id == 20
|
|
|
|
|
|
def test_resolve_all_memberships_inactive_no_effective_club():
|
|
cur = object()
|
|
ctx = resolve_tenant_context(
|
|
cur,
|
|
profile_id=9,
|
|
global_role="user",
|
|
header_raw=None,
|
|
memberships=[{"id": 10, "membership_status": "inactive"}],
|
|
stored_active_club_id=10,
|
|
invalid_header_policy="ignore",
|
|
)
|
|
assert ctx.club_ids == frozenset()
|
|
assert ctx.effective_club_id is None
|