Pārlūkot izejas kodu

Plug database connection leak. Script bindings no longer use default connection.

Neal Wilson 11 gadus atpakaļ
vecāks
revīzija
be18697e70
1 mainītis faili ar 40 papildinājumiem un 48 dzēšanām
  1. 40
    48
      src/typica.w

+ 40
- 48
src/typica.w Parādīt failu

@@ -3369,7 +3369,7 @@ class SqlQueryConnection : public QSqlQuery@/
3369 3369
 	public:@/
3370 3370
 		SqlQueryConnection(const QString &query = QString());
3371 3371
 		~SqlQueryConnection();
3372
-		QSqlQuery* operator->();
3372
+		QSqlQuery* operator->() const;
3373 3373
 	private:@/
3374 3374
 		QString connection;
3375 3375
 		QSqlQuery *q;
@@ -3409,7 +3409,7 @@ SqlQueryConnection::~SqlQueryConnection()
3409 3409
 object.
3410 3410
 
3411 3411
 @<SqlQueryConnection implementation@>=
3412
-QSqlQuery* SqlQueryConnection::operator->()
3412
+QSqlQuery* SqlQueryConnection::operator->() const
3413 3413
 {
3414 3414
 	return q;
3415 3415
 }
@@ -3448,8 +3448,9 @@ value.
3448 3448
 @<Functions for scripting@>=
3449 3449
 QScriptValue constructQSqlQuery(QScriptContext *, QScriptEngine *engine)
3450 3450
 {
3451
+	SqlQueryConnection *obj = new SqlQueryConnection();
3451 3452
 	QScriptValue object =
3452
-	     engine->toScriptValue<void *>(new SqlQueryConnection());
3453
+	     engine->toScriptValue<void *>(obj);
3453 3454
 	setQSqlQueryProperties(object, engine);
3454 3455
 	return object;
3455 3456
 }
@@ -3478,40 +3479,40 @@ void setQSqlQueryProperties(QScriptValue value, QScriptEngine *engine)
3478 3479
 @<Functions for scripting@>=
3479 3480
 QScriptValue QSqlQuery_exec(QScriptContext *context, QScriptEngine *engine)
3480 3481
 {
3481
-	SqlQueryConnection *query = getself<SqlQueryConnection *>(context);
3482
+	QSqlQuery *q = getself<SqlQueryConnection *>(context)->operator->();
3482 3483
 	QScriptValue retval;
3483 3484
 	if(context->argumentCount() == 1)
3484 3485
 	{
3485 3486
 		retval = QScriptValue(engine,
3486
-		                      query->exec(argument<QString>(0, context)));
3487
+		                      q->exec(argument<QString>(0, context)));
3487 3488
 	}
3488 3489
 	else
3489 3490
 	{
3490
-		retval = QScriptValue(engine, query->exec());
3491
+		retval = QScriptValue(engine, q->exec());
3491 3492
 	}
3492
-	if(query->lastError().isValid())
3493
+	if(q->lastError().isValid())
3493 3494
 	{
3494
-		qDebug() << query->lastQuery();
3495
-		qDebug() << query->lastError().text();
3495
+		qDebug() << q->lastQuery();
3496
+		qDebug() << q->lastError().text();
3496 3497
 	}
3497 3498
 	return retval;
3498 3499
 }
3499 3500
 
3500 3501
 QScriptValue QSqlQuery_executedQuery(QScriptContext *context, QScriptEngine *)
3501 3502
 {
3502
-	SqlQueryConnection *query = getself<SqlQueryConnection *>(context);
3503
+	QSqlQuery *query = getself<SqlQueryConnection *>(context)->operator->();
3503 3504
 	return QScriptValue(query->lastQuery());
3504 3505
 }
3505 3506
 
3506 3507
 QScriptValue QSqlQuery_next(QScriptContext *context, QScriptEngine *engine)
3507 3508
 {
3508
-	SqlQueryConnection *query = getself<SqlQueryConnection *>(context);
3509
+	QSqlQuery *query = getself<SqlQueryConnection *>(context)->operator->();
3509 3510
 	return QScriptValue(engine, query->next());
3510 3511
 }
3511 3512
 
3512 3513
 QScriptValue QSqlQuery_value(QScriptContext *context, QScriptEngine *engine)
3513 3514
 {
3514
-	SqlQueryConnection *query = getself<SqlQueryConnection *>(context);
3515
+	QSqlQuery *query = getself<SqlQueryConnection *>(context)->operator->();
3515 3516
 	return QScriptValue(engine,
3516 3517
 	                    query->value(argument<int>(0, context)).toString());
3517 3518
 }
@@ -3522,13 +3523,13 @@ data available in a named file, or data from any open |QIODevice|.
3522 3523
 @<Functions for scripting@>=
3523 3524
 QScriptValue QSqlQuery_prepare(QScriptContext *context, QScriptEngine *engine)
3524 3525
 {
3525
-	SqlQueryConnection *query = getself<SqlQueryConnection *>(context);
3526
+	QSqlQuery *query = getself<SqlQueryConnection *>(context)->operator->();
3526 3527
 	return QScriptValue(engine, query->prepare(argument<QString>(0, context)));
3527 3528
 }
3528 3529
 
3529 3530
 QScriptValue QSqlQuery_bind(QScriptContext *context, QScriptEngine *)
3530 3531
 {
3531
-	SqlQueryConnection *query = getself<SqlQueryConnection *>(context);
3532
+	QSqlQuery *query = getself<SqlQueryConnection *>(context)->operator->();
3532 3533
 	query->bindValue(argument<QString>(0, context),
3533 3534
 	                 argument<QVariant>(1, context));
3534 3535
 	return QScriptValue();
@@ -3537,7 +3538,7 @@ QScriptValue QSqlQuery_bind(QScriptContext *context, QScriptEngine *)
3537 3538
 QScriptValue QSqlQuery_bindFileData(QScriptContext *context,
3538 3539
                                     QScriptEngine *)
3539 3540
 {
3540
-	SqlQueryConnection *query = getself<SqlQueryConnection *>(context);
3541
+	QSqlQuery *query = getself<SqlQueryConnection *>(context)->operator->();
3541 3542
 	QString placeholder = argument<QString>(0, context);
3542 3543
 	QString filename = argument<QString>(1, context);
3543 3544
 	QFile file(filename);
@@ -3554,7 +3555,7 @@ QScriptValue QSqlQuery_bindFileData(QScriptContext *context,
3554 3555
 QScriptValue QSqlQuery_bindDeviceData(QScriptContext *context,
3555 3556
                                       QScriptEngine *)
3556 3557
 {
3557
-	SqlQueryConnection *query = getself<SqlQueryConnection *>(context);
3558
+	QSqlQuery *query = getself<SqlQueryConnection *>(context)->operator->();
3558 3559
 	QString placeholder = argument<QString>(0, context);
3559 3560
 	QIODevice *device = argument<QIODevice *>(1, context);
3560 3561
 	device->reset();
@@ -3680,13 +3681,14 @@ host environment. The function is now depreciated and should not be used.
3680 3681
 @<Functions for scripting@>=
3681 3682
 QScriptValue annotationFromRecord(QScriptContext *context, QScriptEngine *)
3682 3683
 {
3683
-	SqlQueryConnection query;
3684
+	SqlQueryConnection h;
3685
+	QSqlQuery *query = h.operator->();
3684 3686
 	QString q = "SELECT file FROM files WHERE id = :file";
3685
-	query.prepare(q);
3686
-	query.bindValue(":file", argument<int>(0, context));
3687
-	query.exec();
3688
-	query.next();
3689
-	QByteArray array = query.value(0).toByteArray();
3687
+	query->prepare(q);
3688
+	query->bindValue(":file", argument<int>(0, context));
3689
+	query->exec();
3690
+	query->next();
3691
+	QByteArray array = query->value(0).toByteArray();
3690 3692
 	QBuffer buffer(&array);
3691 3693
 	buffer.open(QIODevice::ReadOnly);
3692 3694
 	QXmlQuery xquery;
@@ -11798,28 +11800,17 @@ QDomDocument* Application::configuration()
11798 11800
 @ The |database()| method provides access to a database connection for use by
11799 11801
 database aware widgets.
11800 11802
 
11801
-\danger Behavior observed on Linux is that this does create a new connection
11802
-which the caller will successfully open, but a |QSqlQuery| created with the
11803
-newly opened |QSqlDatabase| will instead continue to execute queries on the
11804
-default connection instead of the new connection. Replacing the call to
11805
-|QSqlDatabase::database()| with one that does not open the default connection
11806
-or rather than cloning that connection creating a new non-default connection
11807
-results in query execution failing because the connection is not open despite
11808
-the call to |open()| succeeding and |isValid()| and |isOpen()| both returning
11809
-true. If this behavior can be replicated on other platforms, this entire
11810
-exercise would be pointless. At present I believe this to be a bug in Qt, but I
11811
-have not identified it.
11812
-
11813 11803
 @<Application Implementation@>=
11814 11804
 QSqlDatabase Application::database()
11815 11805
 {
11816 11806
 	QString connectionName;
11817
-	QSqlDatabase connection = QSqlDatabase::database();
11807
+	QSqlDatabase connection =
11808
+		QSqlDatabase::database(QLatin1String(QSqlDatabase::defaultConnection), false);
11818 11809
 	do
11819 11810
 	{
11820 11811
 		connectionName = QUuid::createUuid().toString();
11821 11812
 	} while (QSqlDatabase::connectionNames().contains(connectionName));
11822
-	return QSqlDatabase::cloneDatabase(connection, connectionName);
11813
+	return QSqlDatabase::cloneDatabase(connection, QString(connectionName));
11823 11814
 }
11824 11815
 
11825 11816
 @** Table editor for ordered arrays with SQL relations.
@@ -12265,7 +12256,8 @@ the combo box with the results.
12265 12256
 @<SqlComboBox Implementation@>=
12266 12257
 void SqlComboBox::addSqlOptions(QString query)
12267 12258
 {
12268
-	SqlQueryConnection *dbquery = new SqlQueryConnection;
12259
+	SqlQueryConnection h;
12260
+	QSqlQuery *dbquery = h.operator->();
12269 12261
 	if(!dbquery->exec(query))
12270 12262
 	{
12271 12263
 		QSqlError error = dbquery->lastError();
@@ -12285,7 +12277,6 @@ void SqlComboBox::addSqlOptions(QString query)
12285 12277
 		}
12286 12278
 		addItem(displayValue, dataValue);
12287 12279
 	}
12288
-	delete dbquery;
12289 12280
 }
12290 12281
 
12291 12282
 @ The constructor initializes some private member data. A size policy is also
@@ -13207,36 +13198,37 @@ placeholders that have not yet had values bound to them), there will be no
13207 13198
 change to the table and the next child element, if any, will be processed.
13208 13199
 
13209 13200
 @<Add SQL query results to report table@>=
13210
-SqlQueryConnection query;
13211
-query.prepare(currentElement.text());
13201
+SqlQueryConnection h;
13202
+QSqlQuery *query = h.operator->();
13203
+query->prepare(currentElement.text());
13212 13204
 foreach(QString key, bindings.uniqueKeys())
13213 13205
 {
13214 13206
 	if(currentElement.text().contains(key))
13215 13207
 	{
13216
-		query.bindValue(key, bindings.value(key));
13208
+		query->bindValue(key, bindings.value(key));
13217 13209
 	}
13218 13210
 }
13219
-query.exec();
13220
-if(!query.next())
13211
+query->exec();
13212
+if(!query->next())
13221 13213
 {
13222 13214
 	continue;
13223 13215
 }
13224
-if(query.record().count() > columns)
13216
+if(query->record().count() > columns)
13225 13217
 {
13226
-	table->appendColumns(query.record().count() - columns);
13218
+	table->appendColumns(query->record().count() - columns);
13227 13219
 }
13228 13220
 do
13229 13221
 {
13230 13222
 	table->appendRows(1);
13231 13223
 	rows++;
13232 13224
 	currentRow++;
13233
-	for(int j = 0; j < query.record().count(); j++)
13225
+	for(int j = 0; j < query->record().count(); j++)
13234 13226
 	{
13235 13227
 		QTextTableCell cell = table->cellAt(currentRow, j);
13236 13228
 		cursor = cell.firstCursorPosition();
13237
-		cursor.insertText(query.value(j).toString());
13229
+		cursor.insertText(query->value(j).toString());
13238 13230
 	}
13239
-} while(query.next());
13231
+} while(query->next());
13240 13232
 
13241 13233
 @ It is sometimes desirable to add fixed data such as column headers to a table.
13242 13234
 This is done with the {\tt <row>} element.

Notiek ielāde…
Atcelt
Saglabāt