[Python-checkins] bpo-44976: Lazy creation of sqlite3 result rows (GH-27884)
pablogsal
webhook-mailer at python.org
Wed Aug 25 06:28:56 EDT 2021
https://github.com/python/cpython/commit/3df0fc89bc2714f5ef03e36a926bc795dcd5e05a
commit: 3df0fc89bc2714f5ef03e36a926bc795dcd5e05a
branch: main
author: Erlend Egeberg Aasland <erlend.aasland at innova.no>
committer: pablogsal <Pablogsal at gmail.com>
date: 2021-08-25T11:28:47+01:00
summary:
bpo-44976: Lazy creation of sqlite3 result rows (GH-27884)
files:
M Modules/_sqlite/cursor.c
M Modules/_sqlite/cursor.h
diff --git a/Modules/_sqlite/cursor.c b/Modules/_sqlite/cursor.c
index e418cafb4feb6..8b830ec767b5d 100644
--- a/Modules/_sqlite/cursor.c
+++ b/Modules/_sqlite/cursor.c
@@ -53,7 +53,6 @@ pysqlite_cursor_init_impl(pysqlite_Cursor *self,
Py_INCREF(connection);
Py_XSETREF(self->connection, connection);
Py_CLEAR(self->statement);
- Py_CLEAR(self->next_row);
Py_CLEAR(self->row_cast_map);
Py_INCREF(Py_None);
@@ -94,7 +93,6 @@ cursor_traverse(pysqlite_Cursor *self, visitproc visit, void *arg)
Py_VISIT(self->lastrowid);
Py_VISIT(self->row_factory);
Py_VISIT(self->statement);
- Py_VISIT(self->next_row);
return 0;
}
@@ -111,7 +109,6 @@ cursor_clear(pysqlite_Cursor *self)
pysqlite_statement_reset(self->statement);
Py_CLEAR(self->statement);
}
- Py_CLEAR(self->next_row);
return 0;
}
@@ -489,8 +486,6 @@ _pysqlite_query_execute(pysqlite_Cursor* self, int multiple, PyObject* operation
self->locked = 1;
self->reset = 0;
- Py_CLEAR(self->next_row);
-
if (multiple) {
if (PyIter_Check(second_argument)) {
/* iterator */
@@ -658,11 +653,7 @@ _pysqlite_query_execute(pysqlite_Cursor* self, int multiple, PyObject* operation
}
}
- if (rc == SQLITE_ROW) {
- self->next_row = _pysqlite_fetch_one_row(self);
- if (self->next_row == NULL)
- goto error;
- } else if (rc == SQLITE_DONE && !multiple) {
+ if (rc == SQLITE_DONE && !multiple) {
pysqlite_statement_reset(self->statement);
Py_CLEAR(self->statement);
}
@@ -821,10 +812,6 @@ pysqlite_cursor_executescript_impl(pysqlite_Cursor *self,
static PyObject *
pysqlite_cursor_iternext(pysqlite_Cursor *self)
{
- PyObject* next_row_tuple;
- PyObject* next_row;
- int rc;
-
if (!check_cursor(self)) {
return NULL;
}
@@ -835,53 +822,40 @@ pysqlite_cursor_iternext(pysqlite_Cursor *self)
return NULL;
}
- if (!self->next_row) {
- if (self->statement) {
- (void)pysqlite_statement_reset(self->statement);
- Py_CLEAR(self->statement);
- }
+ if (self->statement == NULL) {
return NULL;
}
- next_row_tuple = self->next_row;
- assert(next_row_tuple != NULL);
- self->next_row = NULL;
-
- if (self->row_factory != Py_None) {
- next_row = PyObject_CallFunction(self->row_factory, "OO", self, next_row_tuple);
- if (next_row == NULL) {
- self->next_row = next_row_tuple;
- return NULL;
- }
- Py_DECREF(next_row_tuple);
- } else {
- next_row = next_row_tuple;
+ sqlite3_stmt *stmt = self->statement->st;
+ assert(stmt != NULL);
+ if (sqlite3_data_count(stmt) == 0) {
+ (void)pysqlite_statement_reset(self->statement);
+ Py_CLEAR(self->statement);
+ return NULL;
}
- if (self->statement) {
- rc = pysqlite_step(self->statement->st);
- if (PyErr_Occurred()) {
- (void)pysqlite_statement_reset(self->statement);
- Py_DECREF(next_row);
- return NULL;
- }
- if (rc != SQLITE_DONE && rc != SQLITE_ROW) {
- (void)pysqlite_statement_reset(self->statement);
- Py_DECREF(next_row);
- _pysqlite_seterror(self->connection->state, self->connection->db);
- return NULL;
- }
-
- if (rc == SQLITE_ROW) {
- self->next_row = _pysqlite_fetch_one_row(self);
- if (self->next_row == NULL) {
- (void)pysqlite_statement_reset(self->statement);
- return NULL;
- }
- }
+ PyObject *row = _pysqlite_fetch_one_row(self);
+ if (row == NULL) {
+ return NULL;
}
-
- return next_row;
+ int rc = pysqlite_step(stmt);
+ if (rc == SQLITE_DONE) {
+ (void)pysqlite_statement_reset(self->statement);
+ }
+ else if (rc != SQLITE_ROW) {
+ (void)_pysqlite_seterror(self->connection->state,
+ self->connection->db);
+ Py_DECREF(row);
+ return NULL;
+ }
+ if (!Py_IsNone(self->row_factory)) {
+ PyObject *factory = self->row_factory;
+ PyObject *args[] = { (PyObject *)self, row, };
+ PyObject *new_row = PyObject_Vectorcall(factory, args, 2, NULL);
+ Py_DECREF(row);
+ row = new_row;
+ }
+ return row;
}
/*[clinic input]
diff --git a/Modules/_sqlite/cursor.h b/Modules/_sqlite/cursor.h
index 29f52b92189be..d26d20a9fc5ea 100644
--- a/Modules/_sqlite/cursor.h
+++ b/Modules/_sqlite/cursor.h
@@ -46,9 +46,6 @@ typedef struct
int locked;
int initialized;
- /* the next row to be returned, NULL if no next row available */
- PyObject* next_row;
-
PyObject* in_weakreflist; /* List of weak references */
} pysqlite_Cursor;
More information about the Python-checkins
mailing list