In PostgreSQL lastRowId is _not_ always zero

Sandino Araico Sánchez <[email protected]> Mon, 15 Jun 2020 19:53:36 -0500
Newsgroups gmane.mail.imap.dbmail.devel
Message-ID <[email protected]>
This is a multi-part message in MIME format.
--------------4492FCE89BF5175649A81D61
Content-Type: text/plain; charset=utf-8; format=flowed
Content-Transfer-Encoding: quoted-printable

I have been using this patch since 2015 because of db_insert_result()=20
returning the wrong id.

I have just compiled dbmail and got the same errors on dbmail-lmtp=20
trying to insert a message.

Are there any other dbmail with postgresql users working fine?

Is there any objection on always fetching the first row when using=20
postgresql?

--=20
Sandino Araico S=C3=A1nchez
http://sandino.net


--------------4492FCE89BF5175649A81D61
Content-Type: text/x-patch; charset=UTF-8;
 name="3.2-pgsql-RETURNING.patch"
Content-Transfer-Encoding: 7bit
Content-Disposition: attachment;
 filename="3.2-pgsql-RETURNING.patch"

diff -uriN dbmail-3.2.2.orig/src/dm_db.c dbmail-3.2.2/src/dm_db.c
--- dbmail-3.2.2.orig/src/dm_db.c	2014-12-20 16:32:38.000000000 -0600
+++ dbmail-3.2.2/src/dm_db.c	2015-04-03 17:43:45.000000000 -0600
@@ -568,16 +568,43 @@
 
 	if (! db_result_next(r)) { /* ignore */ }
 
+	/* In PostgreSQL 9.1 lastRowId is _not_ always zero
+	 *
+dbmail=# INSERT INTO dbmail_physmessage (internal_date) VALUES 
+dbmail-# (TO_TIMESTAMP('2013-07-20 07:22:34'::text, 'YYYY-MM-DD HH24:MI:SS')) RETURNING id;
+    id    
+----------
+ 29196224
+(1 row)
+
+INSERT 0 1
+dbmail=# INSERT INTO dbmail_messages(mailbox_idnr, physmessage_id, unique_id,recent_flag, status) VALUES (10993, 29196223, 'acc98da420bfe6d3dc2c707a9863001c', 1, 5) RETURNING message_idnr;
+ message_idnr 
+--------------
+     36650725
+(1 row)
+
+INSERT 82105867 1
+	 *
+	 * Connection_lastRowId(c) is returning the OID instead of 
+	 * the message_idnr we are expecting.
+	 * However, we are expecting only one row to be returned so 
+	 * we should always use db_result_get_u64(r, 0);
+	 */
+	if (db_params.db_driver == DM_DRIVER_POSTGRESQL) {
+		id = db_result_get_u64(r, 0); // postgresql
+	}
+
 	// lastRowId is always zero for pgsql tables without OIDs
 	// or possibly for sqlite after calling executeQuery but 
 	// before calling db_result_next
 
-	if ((id = (uint64_t )Connection_lastRowId(c)) == 0) { // mysql
+	else if ((id = (uint64_t )Connection_lastRowId(c)) == 0) { // mysql
 		// but if we're using 'RETURNING id' clauses on inserts
 		// or we're using the sqlite backend, we can do this
 
 		if ((id = (uint64_t )Connection_lastRowId(c)) == 0) // sqlite
-			id = db_result_get_u64(r, 0); // postgresql
+			id = db_result_get_u64(r, 0); // postgresql - should not get this far
 	}
 	assert(id);
 	return id;

--------------4492FCE89BF5175649A81D61
Content-Type: text/plain; charset="utf-8"
MIME-Version: 1.0
Content-Transfer-Encoding: base64
Content-Disposition: inline

X19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX19fX18KRGJtYWlsLWRl
diBtYWlsaW5nIGxpc3QKRGJtYWlsLWRldkBsaXN0cy5uZmcubmwKaHR0cHM6Ly9saXN0cy5uZmcu
bmwvY2dpLWJpbi9tYWlsbWFuL2xpc3RpbmZvL2RibWFpbC1kZXYK

--------------4492FCE89BF5175649A81D61--