Files
fast-next-template/backend/tests/test_init_db.py
Felipe Cardoso 92a8699479 Convert password reset and auth dependencies tests to async
- Refactored all `password reset` and `auth dependency` tests to utilize async patterns for compatibility with async database sessions.
- Enhanced test fixtures with `pytest-asyncio` to support asynchronous database operations.
- Improved user handling with async context management for `test_user` and `async_mock_user`.
- Introduced `await` syntax for route calls, token generation, and database transactions in test cases.
2025-10-31 22:31:01 +01:00

224 lines
8.5 KiB
Python
Executable File

# tests/test_init_db.py
import pytest
from unittest.mock import patch, MagicMock
from sqlalchemy.orm import Session
from app.init_db import init_db
from app.models.user import User
from app.schemas.users import UserCreate
class TestInitDB:
"""Tests for database initialization"""
def test_init_db_creates_superuser_when_not_exists(self, db_session, monkeypatch):
"""Test that init_db creates superuser when it doesn't exist"""
# Set environment variables
monkeypatch.setenv("FIRST_SUPERUSER_EMAIL", "admin@test.com")
monkeypatch.setenv("FIRST_SUPERUSER_PASSWORD", "TestPassword123!")
# Reload settings to pick up environment variables
from app.core import config
import importlib
importlib.reload(config)
from app.core.config import settings
# Mock user_crud to return None (user doesn't exist)
with patch('app.init_db.user_crud') as mock_crud:
mock_crud.get_by_email.return_value = None
# Create a mock user to return from create
from datetime import datetime, timezone
import uuid
mock_user = User(
id=uuid.uuid4(),
email="admin@test.com",
password_hash="hashed",
first_name="Admin",
last_name="User",
is_active=True,
is_superuser=True,
created_at=datetime.now(timezone.utc),
updated_at=datetime.now(timezone.utc)
)
mock_crud.create.return_value = mock_user
# Call init_db
user = init_db(db_session)
# Verify user was created
assert user is not None
assert user.email == "admin@test.com"
assert user.is_superuser is True
mock_crud.create.assert_called_once()
def test_init_db_returns_existing_superuser(self, db_session, monkeypatch):
"""Test that init_db returns existing superuser without creating new one"""
# Set environment variables
monkeypatch.setenv("FIRST_SUPERUSER_EMAIL", "existing@test.com")
monkeypatch.setenv("FIRST_SUPERUSER_PASSWORD", "TestPassword123!")
# Reload settings
from app.core import config
import importlib
importlib.reload(config)
# Mock user_crud to return existing user
with patch('app.init_db.user_crud') as mock_crud:
from datetime import datetime, timezone
import uuid
existing_user = User(
id=uuid.uuid4(),
email="existing@test.com",
password_hash="hashed",
first_name="Existing",
last_name="User",
is_active=True,
is_superuser=True,
created_at=datetime.now(timezone.utc),
updated_at=datetime.now(timezone.utc)
)
mock_crud.get_by_email.return_value = existing_user
# Call init_db
user = init_db(db_session)
# Verify existing user was returned
assert user is not None
assert user.email == "existing@test.com"
# create should NOT be called
mock_crud.create.assert_not_called()
def test_init_db_uses_defaults_when_env_not_set(self, db_session):
"""Test that init_db uses default credentials when env vars not set"""
# Mock settings to return None for superuser credentials
with patch('app.init_db.settings') as mock_settings:
mock_settings.FIRST_SUPERUSER_EMAIL = None
mock_settings.FIRST_SUPERUSER_PASSWORD = None
# Mock user_crud
with patch('app.init_db.user_crud') as mock_crud:
mock_crud.get_by_email.return_value = None
from datetime import datetime, timezone
import uuid
mock_user = User(
id=uuid.uuid4(),
email="admin@example.com",
password_hash="hashed",
first_name="Admin",
last_name="User",
is_active=True,
is_superuser=True,
created_at=datetime.now(timezone.utc),
updated_at=datetime.now(timezone.utc)
)
mock_crud.create.return_value = mock_user
# Call init_db
with patch('app.init_db.logger') as mock_logger:
user = init_db(db_session)
# Verify default email was used
mock_crud.get_by_email.assert_called_with(db_session, email="admin@example.com")
# Verify warning was logged since credentials not set
assert mock_logger.warning.called
def test_init_db_handles_creation_error(self, db_session, monkeypatch):
"""Test that init_db handles errors during user creation"""
# Set environment variables
monkeypatch.setenv("FIRST_SUPERUSER_EMAIL", "admin@test.com")
monkeypatch.setenv("FIRST_SUPERUSER_PASSWORD", "TestPassword123!")
# Reload settings
from app.core import config
import importlib
importlib.reload(config)
# Mock user_crud to raise an exception
with patch('app.init_db.user_crud') as mock_crud:
mock_crud.get_by_email.return_value = None
mock_crud.create.side_effect = Exception("Database error")
# Call init_db and expect exception
with pytest.raises(Exception) as exc_info:
init_db(db_session)
assert "Database error" in str(exc_info.value)
def test_init_db_logs_superuser_creation(self, db_session, monkeypatch):
"""Test that init_db logs appropriate messages"""
# Set environment variables
monkeypatch.setenv("FIRST_SUPERUSER_EMAIL", "admin@test.com")
monkeypatch.setenv("FIRST_SUPERUSER_PASSWORD", "TestPassword123!")
# Reload settings
from app.core import config
import importlib
importlib.reload(config)
# Mock user_crud
with patch('app.init_db.user_crud') as mock_crud:
mock_crud.get_by_email.return_value = None
from datetime import datetime, timezone
import uuid
mock_user = User(
id=uuid.uuid4(),
email="admin@test.com",
password_hash="hashed",
first_name="Admin",
last_name="User",
is_active=True,
is_superuser=True,
created_at=datetime.now(timezone.utc),
updated_at=datetime.now(timezone.utc)
)
mock_crud.create.return_value = mock_user
# Call init_db with logger mock
with patch('app.init_db.logger') as mock_logger:
user = init_db(db_session)
# Verify info log was called
assert mock_logger.info.called
info_call_args = str(mock_logger.info.call_args)
assert "Created first superuser" in info_call_args
def test_init_db_logs_existing_user(self, db_session, monkeypatch):
"""Test that init_db logs when user already exists"""
# Set environment variables
monkeypatch.setenv("FIRST_SUPERUSER_EMAIL", "existing@test.com")
monkeypatch.setenv("FIRST_SUPERUSER_PASSWORD", "TestPassword123!")
# Reload settings
from app.core import config
import importlib
importlib.reload(config)
# Mock user_crud to return existing user
with patch('app.init_db.user_crud') as mock_crud:
from datetime import datetime, timezone
import uuid
existing_user = User(
id=uuid.uuid4(),
email="existing@test.com",
password_hash="hashed",
first_name="Existing",
last_name="User",
is_active=True,
is_superuser=True,
created_at=datetime.now(timezone.utc),
updated_at=datetime.now(timezone.utc)
)
mock_crud.get_by_email.return_value = existing_user
# Call init_db with logger mock
with patch('app.init_db.logger') as mock_logger:
user = init_db(db_session)
# Verify info log was called
assert mock_logger.info.called
info_call_args = str(mock_logger.info.call_args)
assert "already exists" in info_call_args.lower()