Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow early commiting transaction from inside the context manager before raising an exception #1063

Open
rijenkii opened this issue Jan 24, 2025 · 0 comments

Comments

@rijenkii
Copy link

Problem

Use case:

async def get_transaction():
    async with db.tx() as tx:
        yield tx

@router.post("/")
async def endpoint(tx: Annotated[Prisma, Depends(get_transaction)]):
    await tx.entity.delete_many()
    if not_good:
        raise HTTPException()
    return "ok"

I require the removal of the entity to be committed, even though the function was interrupted with an exception.

Suggested solution

Add a commit method to the Prisma class:

class Prisma:
    ...
    async def commit(self):
        if self._tx_id:
            await self._engine.commit_transaction(self._tx_id)

Similar function could be added for rollback.

Usage example:

@router.post("/")
async def endpoint(tx: Annotated[Prisma, Depends(get_transaction)]):
    await tx.entity.delete_many()
    if not_good:
        await tx.commit()
        raise HTTPException()
    return "ok"

Alternatives

Instead of calling commit_transaction it may be possible to set an internal flag that will be consulted on the context exit.

Additional context

Currently I am using this function to do what I want:

async def early_commit(tx: prisma.Prisma):
    if tx._tx_id:  # pyright: ignore[reportPrivateUsage]
        await tx._engine.commit_transaction(  # pyright: ignore[reportPrivateUsage]
            tx._tx_id  # pyright: ignore[reportPrivateUsage]
        )
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant