Как имитировать базу данных (SQLModel + FastAPI)Python

Программы на Python
Ответить
Anonymous
 Как имитировать базу данных (SQLModel + FastAPI)

Сообщение Anonymous »

Я хочу протестировать свою конечную точку GraphQL. Для этого мне придется издеваться над базой данных.
from sqlmodel.ext.asyncio.session import AsyncSession
from sqlalchemy.ext.asyncio import create_async_engine
from contextlib import asynccontextmanager
import os

class Database:
def __init__(self) -> None:
self.engine = None

def connect(self) -> None:
if not self.engine:
self.engine = create_async_engine(os.environ.get("DATABASE_URL", "sqlite:///db.sqlite")
)
else:
raise ConnectionAbortedError("Database is already connected")

@asynccontextmanager
async def get_async_session(self):
if not self.engine:
raise ConnectionError("Database is not connected")

async with AsyncSession(self.engine) as session:
try:
yield session
finally:
await session.close()

Я пытался имитировать create_engine в своем тесте,
async def test_register_user_mutation(self, gql_schema: Schema, engine):
with patch("sqlmodel.create_engine") as mock_create_engine:
mock_create_engine.return_value = engine

в приложении
@pytest.fixture(scope="session", autouse=True)
def app() -> FastAPI:
engine = create_engine(
"sqlite://", connect_args={"check_same_thread": False}, poolclass=StaticPool
)
SQLModel.metadata.create_all(engine)

with patch("sqlmodel.create_engine") as mock_create_engine:
mock_create_engine.return_value = engine

from daytistics.main import app

return app

и мне придется издеваться над сеансом
async def test_register_user_mutation(self, gql_schema: Schema, engine):
with patch("sqlmodel.Session", autospec=True) as mock_session_class:
mock_session_class.return_value = Session(engine)

но каждый раз оно записывалось в рабочую базу данных.
Не знаю, полезно ли это, но это моя фабрика приложений:
р>
def create_app() -> FastAPI:
dotenv.load_dotenv()
app = FastAPI()

register_dependencies()

with container.sync_context() as ctx:
db = ctx.resolve(Database)
db.connect()

graphql_router = create_graphql_router()
app.include_router(graphql_router, prefix="/graphql")

return app

app = create_app()

Обновление:
Я пытался использовать обезьяний патч, но он тоже не сработал:
@pytest.fixture(scope="function")
async def mock_db(monkeypatch):
test_engine = create_async_engine(
"sqlite+aiosqlite:///:memory:",
echo=False,
future=True,
connect_args={"check_same_thread": False},
)

async with test_engine.begin() as conn:
await conn.run_sync(SQLModel.metadata.create_all)

def mock_connect(self):
self.engine = test_engine

@asynccontextmanager
async def mock_get_async_session(self):
async with AsyncSession(test_engine) as session:
try:
yield session
finally:
await session.close()

monkeypatch.setattr(Database, "connect", mock_connect)
monkeypatch.setattr(Database, "get_async_session", mock_get_async_session)

return test_engine


Подробнее здесь: https://stackoverflow.com/questions/792 ... el-fastapi
Ответить

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

Вернуться в «Python»