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

Add cursor fluent-style chaining #6

Closed
wants to merge 3 commits into from

Conversation

thegamecracks
Copy link
Contributor

@thegamecracks thegamecracks commented Jun 3, 2021

This allows chaining execute*, fetch*, start, commit, and rollback methods of Cursor/_CursorWithTransaction and also execute* methods of Connection as such:

async with asqlite.connect(':memory:') as conn:
    row = await conn.executescript(
        'CREATE TABLE test (id INTEGER);'
        'INSERT INTO test VALUES (1);'
    ).execute(
        'SELECT * FROM test;'
    ).fetchone()

    async with conn.execute(
            'INSERT INTO test VALUES (2);').execute(
            'SELECT * FROM test;') as c:
        rows = await c.fetchall()

This is related to issue #5 which attempted chaining an execute and fetchone, resulting an an exception due to trying to use a cursor created by the worker thread in the main thread. This PR does not support their syntax however since they are awaiting c.execute(...) by itself, which would still return an sqlite3.Cursor here.

Makes Cursor.execute* methods return itself instead of a sqlite3.Cursor to allow fluent-style chaining.
This allows using only one await to evaluate chained methods, rather than having to await each cursor method in the last commit (which made it not so fluent). Also allows more methods to be chained such as Connection.execute*, Cursor.fetch*, and _CursorWithTransaction methods.
@Rapptz
Copy link
Owner

Rapptz commented Jun 3, 2021

I'm not really big on the implementation here. It feels rather inefficient and bolted on.

The Python ecosystem as a whole is probably unfamiliar with the concept of async chaining like you're doing here. It's definitely foreign and blurs the line on where await should be required so I'm not super big on it. In Rust this is less of a problem since they use .await syntax but in Python chaining like this is verbose.

There's probably some ergonomic tradeoff to be made here but I'm not super into this implementation as it stands.

@Rapptz Rapptz closed this Jun 4, 2021
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

Successfully merging this pull request may close these issues.

2 participants