55
66import uuid
77import warnings
8- from collections .abc import AsyncIterator , Awaitable , Callable , Iterator
8+ from collections .abc import AsyncIterator , Awaitable , Callable , Iterable , Iterator
99from pathlib import Path
1010
1111import aiopg .sa
1212import aiopg .sa .exc
1313import pytest
1414import simcore_postgres_database .cli
1515import sqlalchemy as sa
16+ import sqlalchemy .engine
1617import yaml
1718from aiopg .sa .connection import SAConnection
1819from aiopg .sa .engine import Engine
1920from aiopg .sa .result import ResultProxy , RowProxy
2021from faker import Faker
22+ from pytest_simcore .helpers import postgres_tools
2123from pytest_simcore .helpers .faker_factories import (
2224 random_group ,
2325 random_project ,
@@ -71,20 +73,15 @@ def postgres_service(docker_services, docker_ip, docker_compose_file) -> str:
7173 return dsn
7274
7375
74- @pytest .fixture
75- def make_engine (
76- postgres_service : str ,
77- ) -> Callable [[bool ], Awaitable [Engine ] | sa .engine .base .Engine ]:
78- dsn = postgres_service
79-
80- def _make (is_async = True ) -> Awaitable [Engine ] | sa .engine .base .Engine :
81- return aiopg .sa .create_engine (dsn ) if is_async else sa .create_engine (dsn )
82-
83- return _make
76+ @pytest .fixture (scope = "session" )
77+ def sync_engine (postgres_service : str ) -> Iterable [sqlalchemy .engine .Engine ]:
78+ _engine : sqlalchemy .engine .Engine = sa .create_engine (url = postgres_service )
79+ yield _engine
80+ _engine .dispose ()
8481
8582
8683@pytest .fixture
87- def make_asyncpg_engine (postgres_service : str ) -> Callable [[bool ], AsyncEngine ]:
84+ def _make_asyncpg_engine (postgres_service : str ) -> Callable [[bool ], AsyncEngine ]:
8885 # NOTE: users is responsible of `await engine.dispose()`
8986 dsn = postgres_service .replace ("postgresql://" , "postgresql+asyncpg://" )
9087 minsize = 1
@@ -127,10 +124,10 @@ def db_metadata() -> sa.MetaData:
127124
128125@pytest .fixture (params = ["sqlModels" , "alembicMigration" ])
129126def pg_sa_engine (
130- make_engine : Callable ,
127+ sync_engine : sqlalchemy . engine . Engine ,
131128 db_metadata : sa .MetaData ,
132129 request : pytest .FixtureRequest ,
133- ) -> Iterator [sa .engine .Engine ]:
130+ ) -> Iterator [sqlalchemy .engine .Engine ]:
134131 """
135132 Runs migration to create tables and return a sqlalchemy engine
136133
@@ -144,7 +141,6 @@ def pg_sa_engine(
144141 # the tables, i.e. when no migration mechanism are in place
145142 # Best is therefore to start from scratch and delete all at
146143 # the end
147- sync_engine = make_engine (is_async = False )
148144
149145 # NOTE: ALL is deleted before
150146 db_metadata .drop_all (sync_engine )
@@ -165,22 +161,20 @@ def pg_sa_engine(
165161
166162 yield sync_engine
167163
168- # NOTE: ALL is deleted after
169- with sync_engine .begin () as conn :
170- conn .execute (sa .DDL ("DROP TABLE IF EXISTS alembic_version" ))
171- db_metadata .drop_all (sync_engine )
172- sync_engine .dispose ()
164+ postgres_tools .force_drop_all_tables (sync_engine )
173165
174166
175167@pytest .fixture
176168async def aiopg_engine (
177- pg_sa_engine : sa .engine .Engine , make_engine : Callable
169+ pg_sa_engine : sqlalchemy .engine .Engine ,
170+ postgres_service : str ,
178171) -> AsyncIterator [Engine ]:
179172 """
180173 Return an aiopg.sa engine connected to a responsive and migrated pg database
181174 """
182-
183- aiopg_sa_engine = await make_engine (is_async = True )
175+ # first start sync
176+ assert pg_sa_engine .url .database
177+ assert postgres_service .endswith (pg_sa_engine .url .database )
184178
185179 warnings .warn (
186180 "The 'aiopg_engine' is deprecated since we are replacing `aiopg` library by `sqlalchemy.ext.asyncio`."
@@ -190,12 +184,8 @@ async def aiopg_engine(
190184 stacklevel = 2 ,
191185 )
192186
193- yield aiopg_sa_engine
194-
195- # closes async-engine connections and terminates
196- aiopg_sa_engine .close ()
197- await aiopg_sa_engine .wait_closed ()
198- aiopg_sa_engine .terminate ()
187+ async with aiopg .sa .create_engine (dsn = postgres_service ) as aiopg_sa_engine :
188+ yield aiopg_sa_engine
199189
200190
201191@pytest .fixture
@@ -208,15 +198,15 @@ async def connection(aiopg_engine: Engine) -> AsyncIterator[SAConnection]:
208198@pytest .fixture
209199async def asyncpg_engine ( # <-- WE SHOULD USE THIS ONE
210200 is_pdb_enabled : bool ,
211- pg_sa_engine : sa .engine .Engine ,
212- make_asyncpg_engine : Callable [[bool ], AsyncEngine ],
201+ pg_sa_engine : sqlalchemy .engine .Engine ,
202+ _make_asyncpg_engine : Callable [[bool ], AsyncEngine ],
213203) -> AsyncIterator [AsyncEngine ]:
214204
215205 assert (
216206 pg_sa_engine
217207 ), "Ensures pg db up, responsive, init (w/ tables) and/or migrated"
218208
219- _apg_engine = make_asyncpg_engine (is_pdb_enabled )
209+ _apg_engine = _make_asyncpg_engine (is_pdb_enabled )
220210
221211 yield _apg_engine
222212
@@ -229,9 +219,7 @@ async def asyncpg_engine( # <-- WE SHOULD USE THIS ONE
229219
230220
231221@pytest .fixture
232- def create_fake_group (
233- make_engine : Callable [..., Awaitable [Engine ] | sa .engine .base .Engine ]
234- ) -> Iterator [Callable ]:
222+ def create_fake_group (sync_engine : sqlalchemy .engine .Engine ) -> Iterator [Callable ]:
235223 """factory to create standard group"""
236224 created_ids = []
237225
@@ -250,16 +238,13 @@ async def _creator(conn: SAConnection, **overrides) -> RowProxy:
250238
251239 yield _creator
252240
253- sync_engine = make_engine (is_async = False )
254- assert isinstance (sync_engine , sa .engine .Engine )
241+ assert isinstance (sync_engine , sqlalchemy .engine .Engine )
255242 with sync_engine .begin () as conn :
256243 conn .execute (sa .delete (groups ).where (groups .c .gid .in_ (created_ids )))
257244
258245
259246@pytest .fixture
260- def create_fake_user (
261- make_engine : Callable [..., Awaitable [Engine ] | sa .engine .base .Engine ]
262- ) -> Iterator [Callable ]:
247+ def create_fake_user (sync_engine : sqlalchemy .engine .Engine ) -> Iterator [Callable ]:
263248 """factory to create a user w/ or w/o a standard group"""
264249
265250 created_ids = []
@@ -290,8 +275,7 @@ async def _creator(conn, group: RowProxy | None = None, **overrides) -> RowProxy
290275
291276 yield _creator
292277
293- sync_engine = make_engine (is_async = False )
294- assert isinstance (sync_engine , sa .engine .Engine )
278+ assert isinstance (sync_engine , sqlalchemy .engine .Engine )
295279 with sync_engine .begin () as conn :
296280 conn .execute (users .delete ().where (users .c .id .in_ (created_ids )))
297281
0 commit comments