|
1 | 1 | from collections.abc import Generator |
2 | | -from contextlib import nullcontext |
| 2 | +from unittest.mock import patch |
3 | 3 |
|
4 | 4 | import pytest |
5 | 5 | from _pytest.fixtures import FixtureRequest |
|
11 | 11 | from app.main import app |
12 | 12 | from app.models import Item, User |
13 | 13 | from app.tests.utils.user import authentication_token_from_email |
14 | | -from app.tests.utils.utils import get_superuser_token_headers, patch_password_hashing |
| 14 | +from app.tests.utils.utils import get_superuser_token_headers |
15 | 15 |
|
16 | 16 |
|
17 | | -@pytest.fixture(scope="module", autouse=True) |
| 17 | +@pytest.fixture(scope="module") |
18 | 18 | def disable_password_hashing(request: FixtureRequest) -> Generator[None, None, None]: |
19 | | - """Fixture disabling password hashing |
20 | | -
|
21 | | - Password hashing can be enabled on module level by marking the module with `pytest.mark.enable_password_hashing`. |
| 19 | + """ |
| 20 | + Disable password hashing if no `enable_password_hashing` marker set for module. |
22 | 21 | """ |
23 | 22 |
|
24 | | - with ( |
25 | | - patch_password_hashing("app.core.security") |
26 | | - if all(m.name != "enable_password_hashing" for m in request.node.iter_markers()) |
27 | | - else nullcontext() |
28 | | - ): |
29 | | - yield |
| 23 | + module = request.node.getparent(pytest.Module) |
| 24 | + if not module.get_closest_marker("enable_password_hashing"): |
| 25 | + with ( |
| 26 | + patch("app.core.security.pwd_context.verify", lambda x, y: x == y), |
| 27 | + patch("app.core.security.pwd_context.hash", lambda x: x), |
| 28 | + ): |
| 29 | + yield True |
| 30 | + else: |
| 31 | + yield False # Don't patch if `enable_password_hashing` marker is set |
30 | 32 |
|
31 | 33 |
|
32 | | -@pytest.fixture(scope="session") |
33 | | -def db() -> Generator[Session, None, None]: |
34 | | - """ |
35 | | - Module scoped fixture providing a database session initialized with `init_db`. |
36 | | - """ |
| 34 | +@pytest.fixture(scope="module") |
| 35 | +def db(disable_password_hashing) -> Generator[Session, None, None]: # noqa: ARG001 |
37 | 36 | with Session(engine) as session: |
| 37 | + session.execute( # Recreate user for every module, with\without pwd hashing |
| 38 | + delete(User) |
| 39 | + ) |
| 40 | + init_db(session) |
| 41 | + session.commit() |
38 | 42 | yield session |
39 | 43 | # Cleanup test database |
40 | 44 | session.execute(delete(Item)) |
41 | 45 | session.execute(delete(User)) |
42 | 46 | session.commit() |
43 | 47 |
|
44 | 48 |
|
45 | | -@pytest.fixture(scope="module", autouse=True) |
46 | | -def init_db_fixture(db: Session) -> None: |
47 | | - # note: deleting all users here is required to enable or disable password hashing per test module. |
48 | | - # If we don't delete all users here, the users created during `init_db` will not be re-created and the password will stay (un)hashed, |
49 | | - # leading to possibly failing tests relying on the created user for authentication. |
50 | | - db.execute(delete(Item)) |
51 | | - db.execute(delete(User)) |
52 | | - init_db(db) |
53 | | - db.commit() |
54 | | - |
55 | | - |
56 | 49 | @pytest.fixture(scope="module") |
57 | 50 | def client(db: Session) -> Generator[TestClient, None, None]: # noqa: ARG001 |
58 | | - """ |
59 | | - Module scoped fixture providing a `TestClient` instance. |
60 | | -
|
61 | | - NOTE: This fixture uses the `db` fixture WITHOUT hashing passwords! |
62 | | - """ |
63 | 51 | with TestClient(app) as c: |
64 | 52 | yield c |
65 | 53 |
|
|
0 commit comments