Important: Please read the Qt Code of Conduct -

Can not copy SQLite database to Postgresql

  • I was able to create an SQLite database using the QSql class and associated class and would like to be able to use that when off the LAN but I need to copy that to a Postgresql database when back on the LAN.
    I have been able to access the SQLite database and find the columns and data in the SQLite DB and I can connect to the Postgresql database. I go through a series of steps to create the table in Postgresql from the SQLite DB and do not get any errors but the tables do not appear in Postgresql. I checked in the public schema since I can not find a way to create the schema in Postgresql. The SQLite DB has multiple tables and I want to keep them together in a schema.

    The code I have tried follows.

    QStringList tableList = mSqlDatabase.tables();

    QStringList::iterator tableIter;
    bool submitOk = false;

    tableIter = tableList.begin();
    while (tableIter != tableList.end())
    QSqlRelationalTableModel *srcTableModel = new QSqlRelationalTableModel(this, mSqlDatabase);
    QSqlRelationalTableModel *destTableModel = new QSqlRelationalTableModel(this, copyToDdatabase);

    if ((srcTableModel != NULL) && (destTableModel != NULL))
    	int srcColumns = srcTableModel->columnCount();
    	QSqlRecord srcRecord = srcTableModel->record();
    	QSqlRecord destRecord;
    	for (int index = 0; index < srcColumns; index++)
    		QString fieldName = srcRecord.fieldName(index);
    		QSqlField srcField = srcRecord.field(fieldName);
    		QSqlField field = QSqlField(srcField);
    	destTableModel->insertRecord(-1, destRecord);
    	submitOk = destTableModel->database().commit();
    	for (int index = 0; index < numSrcRows; index++)
    		QSqlRecord record = srcTableModel->record(index);
    		QString fieldName;
    		QVariant value;
    		fieldName = record.fieldName(0);  // for debug only
    		value = record.value(0);  // for debug only
    		destTableModel->insertRecord(index, record);
    	submitOk =destTableModel->submit();
    	submitOk = destTableModel->database().commit();

  • Hello,
    I don't think it's that simple as you try to make it, at least if you want to include the data too.
    Few years ago I had a similar problem and I wrote a function for that purpose. I'm copying-pasting the code from my old post after some reformatting to be readable. Although I have improved the code a bit since then in my own app, this should help you get started (please check the indentation, some fixes may be needed). This function doesn't transfer the schema, but I think it's easy to include it.

    void DbManager::exportTables()
    	QHash<QString,QStringList> tablesWithFields; //It holds the table name and its fields
    	QStringList tables = sourceDb.tables();
    	QSqlQuery query(sourceDb);
    	foreach(const QString &table,tables) {
    	    query.exec(QString("PRAGMA TABLE_INFO(%1)").arg(table));
    	    QStringList fields;
    	    while( {
    		  fields << query.value(1).toString();
    	QFile f(QDir::homePath() + "/myDump.sql"); | QIODevice::Text);
    	QTextStream streamer(&f);
    	//If constraints can't be dropped in the target database, some reordering of 
        //the INSERT statements may be needed
    	QStringList sortedTables = tablesWithFields.keys();
    	streamer << "BEGIN;\n";
    	foreach(const QString &table,sortedTables) {
    		if(table=="sqlite_sequence" /*|| table=="table4", etc*/) continue;
    		QString statement = QString("INSERT INTO %1 VALUES('").arg(table);
    		QStringList fields = tablesWithFields.value(table);
    		QString fieldsString = fields.join(",");
    		query.exec(QString("SELECT %1 FROM %2").arg(fieldsString).arg(table));
    		if(! continue;
    		while( {
    			for(int i=0; i < fields.size(); ++i) {
    				QString value = query.value(i).toString();
    				value.replace("'","''"); //Handle single quotes inside strings
    				if(value.isEmpty()) {
    					value = "NULL";
    					statement.chop(1); //NULL should not appear inside quotes
    				} else {
    			statement.chop(2); //Remove comma and single quote from the end of value group
    			statement.append("),('"); //Close the value group and start a new one
    		statement.chop(3);//Remove comma, opening parenthesis, single quote from the end
    		streamer << statement << ";\n"; //Complete the INSERT statement
    	streamer << "COMMIT;";

    And then batch execute the sql file like this:

    QSqlQuery query(targetDb);
    QFile f(QDir::homePath()+"/myDump.sql"); | QIODevice::Text);
    		qCritical() << "Can't execute sql file: " << query.lastError().text();