Trouble Implementing Database Transactions with asyncmy / aiomysql

72 Views Asked by At

I'm working on a Discord bot using Python and have encountered an issue when trying to implement database transactions with the asyncmy library. My bot runs fine when using normal database operations, but when I attempt to integrate transactions, I encounter errors related to closing the database connection.

Working Setup (without transactions):

# Database Pool Creation
async def create_pool(self):
    self.db_pool = await asyncmy.create_pool(
        host=os.getenv("RDS_HOST"),
        port=int(os.getenv("RDS_PORT")),
        user=os.getenv("RDS_USERNAME"),
        password=os.getenv("RDS_PASSWORD"),
        db=os.getenv("RDS_DATABASE"),
        autocommit=True
    )

# Execute Method
async def execute(self, query, *values):
    async with self.db_pool.acquire() as conn:
        async with conn.cursor() as cur:
            await cur.execute(query, *values)
        await conn.commit()

Issue with Transactions:

When I try to implement a transaction-based method, the bot fails to run, and I get errors like "object NoneType can't be used in 'await' expression." Here's the code I used to handle transactions:

# Start Transaction
async def start_transaction(self):
    conn = await self.db_pool.acquire()
    await conn.begin()
    return conn

# Execute with Transaction Option
async def execute(self, query, *values, conn=None):
    is_transaction = conn is not None
    connection_acquired_here = False

    if not is_transaction:
        conn = await self.db_pool.acquire()
        connection_acquired_here = True

    try:
        async with conn.cursor() as cur:
            await cur.execute(query, *values)

        if not is_transaction:
            await conn.commit()
    except Exception as e:
        if not is_transaction:
            await conn.rollback()
        raise
    finally:
        if connection_acquired_here and conn:
            await conn.close()

# Usage Example
async def create_table_in_transaction(self):
    conn = await self.start_transaction()
    try:
        await self.execute("CREATE TABLE IF NOT EXISTS test_table (...)", conn=conn)
        await conn.commit()
    except Exception as e:
        await conn.rollback()
    finally:
        await conn.close()

Error Received:

When running the bot with the transaction code, it fails with the following error:

TypeError: object NoneType can't be used in 'await' expression

This error occurs at the await conn.close() line in the finally block of the execute method

What am I doing wrong?

0

There are 0 best solutions below