Comments (5)
Hi, I'm traveling this week but sqlalchemy is a pass through to the database here which is deadlocking on two concurrent commands and is extremely normal and typical for postgresql. Alembic migrations should always use a single connection only as well. No bug is illustrated here as yet so let's please continue on the alembic discussion without fanning out multiple bug reports . If some behavior or documentation is not ideal we will open a bug at that point, thanks!
from sqlalchemy.
This seems an asyncpg thing.
This also reproduces:
import asyncio
import asyncpg
url = "postgresql://scott:[email protected]:5432/test"
async def main2():
connection1 = await asyncpg.connect(url)
await connection1.execute("drop table if exists table_1 ")
await connection1.close()
connection1 = await asyncpg.connect(url)
await connection1.execute(
"""CREATE TABLE IF NOT EXISTS table_1 (
id INTEGER NOT NULL,
data VARCHAR NOT NULL
)"""
)
await connection1.close()
connection1 = await asyncpg.connect(url)
connection2 = await asyncpg.connect(url)
async with connection1.transaction() as t:
await connection1.fetch("SELECT 1")
print("here")
await connection2.execute(
"CREATE INDEX CONCURRENTLY ix_1 ON table_1 (data)"
)
if __name__ == "__main__":
asyncio.run(main2())
from sqlalchemy.
For reference psycopg3 works correctly
import asyncio
import psycopg
try:
asyncio.set_event_loop_policy(asyncio.WindowsSelectorEventLoopPolicy())
except AttributeError:
pass
url = "postgresql://scott:[email protected]:5432/test"
async def main2():
async with await psycopg.AsyncConnection.connect(url) as connection1:
await connection1.execute("drop table if exists table_1 ")
await connection1.commit()
async with await psycopg.AsyncConnection.connect(url) as connection1:
await connection1.execute(
"""CREATE TABLE IF NOT EXISTS table_1 (
id INTEGER NOT NULL,
data VARCHAR NOT NULL
)"""
)
await connection1.commit()
async with await psycopg.AsyncConnection.connect(
url
) as connection1, await psycopg.AsyncConnection.connect(
url
) as connection2:
await connection2.set_autocommit(True)
await (await connection1.execute("SELECT 1")).fetchall()
print("here")
await connection2.execute(
"CREATE INDEX CONCURRENTLY ix_1 ON table_1 (data)"
)
if __name__ == "__main__":
asyncio.run(main2())
not really sure what asyncpg is doing here.
from sqlalchemy.
As I understand prepared statements in asyncpg can leave portals that hold old snapshots. And this makes index creation waiting.
https://www.postgresql.org/docs/current/sql-createindex.html
After the second scan, the index build must wait for any transactions that have a snapshot (see Chapter 13) predating the second scan to terminate.
Not sure if it can be fixed but some portals can be closed manually MagicStack/asyncpg#1088
from sqlalchemy.
It seems very strange that those are causing it since the behaviour happens also after closing the connection.
In the asyncpg example the connection that created the table is closed once that's created, it's not the same connection that hold the transaction, so it should not have any old snapshot held
Psycopg also uses prepared statements i think
from sqlalchemy.
Related Issues (20)
- Parameter substitution fails when statement has a postgres style cast HOT 5
- reflecting oracle synonym of synonym over dblink HOT 4
- Changing decimal separator to comma using locale.setlocale causes crash on MSSQL columns of decimal type HOT 3
- Generated syntax error when using funcs in server_default in MySQL
- NoForeignKeysError and AmbiguousForeignKeysError after upgrade to 2.x HOT 5
- selectin_polymorphic does not work for multiple level joined inheritance HOT 2
- ColumnCollection.get(col, default) types as Optional even with default HOT 2
- bulk_save_objects() w/ return defaults writes incorrect identity key HOT 4
- `sqlalchemy.utils.langhelpers.TypingOnly` too rigidly prevents special dunders from appearing HOT 5
- func.count argument typing issue HOT 1
- Bundle labels are wrong for new style select only (query works ?!) HOT 9
- Use of `raise NotImplementedError` instead of `NotImplemented` HOT 1
- Design a Repository pattern with sqlalchemy HOT 1
- Add `name` to `with_polymorphic ` HOT 2
- _JoinedListener can sneak into a metadata collection if Enum adapts itself, which can happen now, prohibiting serialization HOT 2
- TypeAlias cannot be found in type_annotation_map HOT 2
- Typing: of_type method not properly generic. HOT 1
- Add `insert_default` param to `Column` HOT 2
- many to many loaded relation instances partially missing reverse relation
- Add additional information to the `ReflectedColumn`
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from sqlalchemy.