From f4e197d9208eaebfedbe5c6261da6c4616152157 Mon Sep 17 00:00:00 2001 From: Christian Ehrlicher Date: Wed, 23 Oct 2024 19:38:09 +0200 Subject: [PATCH] SQL/PSQL: add full support for uuid column type Add full support for uuid column type by decoding a uuid column directly into a QUuid. Storing a QUuid in a database was already supported for a longer time. Task-number: QTBUG-130389 Change-Id: I1b86749e2317c619b3aa8a4f9292c83c33fdcaad Reviewed-by: Thiago Macieira --- src/plugins/sqldrivers/psql/qsql_psql.cpp | 7 +++ .../sql/kernel/qsqlquery/tst_qsqlquery.cpp | 43 +++++++++++++++++++ 2 files changed, 50 insertions(+) diff --git a/src/plugins/sqldrivers/psql/qsql_psql.cpp b/src/plugins/sqldrivers/psql/qsql_psql.cpp index 33c26896708..f0a730e614e 100644 --- a/src/plugins/sqldrivers/psql/qsql_psql.cpp +++ b/src/plugins/sqldrivers/psql/qsql_psql.cpp @@ -15,6 +15,7 @@ #include #include #include +#include #include #include #include @@ -50,6 +51,7 @@ #define QBITOID 1560 #define QVARBITOID 1562 +#define QUUIDOID 2950 #define VARHDRSZ 4 @@ -371,6 +373,9 @@ static QMetaType qDecodePSQLType(int t) case QBYTEAOID: type = QMetaType::QByteArray; break; + case QUUIDOID: + type = QMetaType::QUuid; + break; default: type = QMetaType::QString; break; @@ -671,6 +676,8 @@ QVariant QPSQLResult::data(int i) qPQfreemem(data); return QVariant(ba); } + case QMetaType::QUuid: + return QUuid::fromString(val); default: qCWarning(lcPsql, "QPSQLResult::data: unhandled data type %d.", type.id()); } diff --git a/tests/auto/sql/kernel/qsqlquery/tst_qsqlquery.cpp b/tests/auto/sql/kernel/qsqlquery/tst_qsqlquery.cpp index 4ed8b494615..be98b7c1909 100644 --- a/tests/auto/sql/kernel/qsqlquery/tst_qsqlquery.cpp +++ b/tests/auto/sql/kernel/qsqlquery/tst_qsqlquery.cpp @@ -270,6 +270,10 @@ private slots: // invalidQuery() if run later; so put this one last ! void prematureExec_data() { generic_data(); } void prematureExec(); + + void uuid_data() { generic_data(); } + void uuid(); + private: // returns all database connections void generic_data(const QString &engine=QString()); @@ -5238,6 +5242,45 @@ void tst_QSqlQuery::psqlJsonOperator() QCOMPARE(qry.value(1).toByteArray(), "{\"b\": [3, 4]}"); } +void tst_QSqlQuery::uuid() +{ + QFETCH(QString, dbName); + QSqlDatabase db = QSqlDatabase::database(dbName); + CHECK_DATABASE(db); + if (tst_Databases::getDatabaseType(db) != QSqlDriver::PostgreSQL && + tst_Databases::getDatabaseType(db) != QSqlDriver::MimerSQL) + QSKIP("UUID only supported by PostgreSQL and MimerSQL"); + + TableScope ts(db, "uuid", __FILE__); + const QString &tableName = ts.tableName(); + const QUuid uuid1(QUuid::createUuid()); + const QUuid uuid2(QUuid::createUuid()); + + QSqlQuery qry(db); + QVERIFY_SQL(qry, exec("CREATE TABLE " + tableName + " (id integer, uuidcol uuid)")); + auto tableRecord = db.record(tableName); + QCOMPARE(tableRecord.value(0).metaType().id(), QMetaType::Int); + QCOMPARE(tableRecord.value(1).metaType().id(), QMetaType::QUuid); + + QString stmt = + "INSERT INTO " + tableName + " (id, uuidcol) VALUES (1, '" + uuid1.toString() + "')"; + QVERIFY_SQL(qry, exec(stmt)); + QVERIFY_SQL(qry, prepare("INSERT INTO " + tableName + " (id, uuidcol) VALUES (:id, :uuid)")); + qry.bindValue(":id", 2); + qry.bindValue(":uuid", uuid2); + QVERIFY_SQL(qry, exec()); + QVERIFY_SQL(qry, exec("SELECT id, uuidcol FROM " + tableName + " ORDER BY id")); + QVERIFY_SQL(qry, next()); + QCOMPARE(qry.value(0).toInt(), 1); + QCOMPARE(qry.value(0).metaType().id(), QMetaType::Int); + QCOMPARE(qry.value(1).toUuid(), uuid1); + QCOMPARE(qry.value(1).metaType().id(), QMetaType::QUuid); + QVERIFY_SQL(qry, next()); + QCOMPARE(qry.value(0).toInt(), 2); + QCOMPARE(qry.value(0).metaType().id(), QMetaType::Int); + QCOMPARE(qry.value(1).toUuid(), uuid2); + QCOMPARE(qry.value(1).metaType().id(), QMetaType::QUuid); +} QTEST_MAIN(tst_QSqlQuery) #include "tst_qsqlquery.moc"