@@ -704,10 +704,66 @@ async def test_database_url_interface(database_url):
704
704
@pytest .mark .parametrize ("database_url" , DATABASE_URLS )
705
705
@async_adapter
706
706
async def test_concurrent_access_on_single_connection (database_url ):
707
+ if database_url .dialect != "postgresql" :
708
+ pytest .skip ("Test requires `pg_sleep()`" )
709
+
707
710
async with Database (database_url , force_rollback = True ) as database :
708
711
709
712
async def db_lookup ():
710
- if str (database_url ).startswith ("postgresql" ):
711
- await database .fetch_one ("SELECT pg_sleep(1)" )
713
+ await database .fetch_one ("SELECT pg_sleep(1)" )
712
714
713
715
await asyncio .gather (db_lookup (), db_lookup ())
716
+
717
+
718
+ @pytest .mark .parametrize ("database_url" , DATABASE_URLS )
719
+ @async_adapter
720
+ async def test_iterate_outside_transaction_with_values (database_url ):
721
+ """
722
+ Ensure `iterate()` works even without a transaction on all drivers.
723
+ The asyncpg driver relies on server-side cursors without hold
724
+ for iteration, which requires a transaction to be created.
725
+ This is mentionned in both their documentation and their test suite.
726
+ """
727
+
728
+ database_url = DatabaseURL (database_url )
729
+ if database_url .dialect == "mysql" :
730
+ pytest .skip ("MySQL does not support `FROM (VALUES ...)` (F641)" )
731
+
732
+ async with Database (database_url ) as database :
733
+ query = "SELECT * FROM (VALUES (1), (2), (3), (4), (5)) as t"
734
+ iterate_results = []
735
+
736
+ async for result in database .iterate (query = query ):
737
+ iterate_results .append (result )
738
+
739
+ assert len (iterate_results ) == 5
740
+ assert iterate_results == [(1 ,), (2 ,), (3 ,), (4 ,), (5 ,)]
741
+
742
+
743
+ @pytest .mark .parametrize ("database_url" , DATABASE_URLS )
744
+ @async_adapter
745
+ async def test_iterate_outside_transaction_with_temp_table (database_url ):
746
+ """
747
+ Same as test_iterate_outside_transaction_with_values but uses a
748
+ temporary table instead of a list of values.
749
+ """
750
+
751
+ database_url = DatabaseURL (database_url )
752
+ if database_url .dialect == "sqlite" :
753
+ pytest .skip ("SQLite interface does not work with temporary tables." )
754
+
755
+ async with Database (database_url ) as database :
756
+ query = "CREATE TEMPORARY TABLE no_transac(num INTEGER)"
757
+ await database .execute (query )
758
+
759
+ query = "INSERT INTO no_transac(num) VALUES (1), (2), (3), (4), (5)"
760
+ await database .execute (query )
761
+
762
+ query = "SELECT * FROM no_transac"
763
+ iterate_results = []
764
+
765
+ async for result in database .iterate (query = query ):
766
+ iterate_results .append (result )
767
+
768
+ assert len (iterate_results ) == 5
769
+ assert iterate_results == [(1 ,), (2 ,), (3 ,), (4 ,), (5 ,)]
0 commit comments