Skip to content

Commit 66ffa5f

Browse files
mgrojoMKleusberg
authored andcommitted
Problems with WITHOUT ROWID tables with PK of string type (sqlitebrowser#1559)
* Problems with WITHOUT ROWID tables with PK of string type This fixes two related problems: - When the PK is updated the hidden column 0 must be updated too, otherwise any further editing of the same row before a table refresh is broken. - When a new record is inserted and the PK has string type we cannot simply make a pseudo auto-increment and insert that value as rowid because that added key would be impossible to update because our UPDATE clause will try to update a column with a string and it contains an integer. In this case it's better to let the user enter the PK value, so the new Add Record dialog is directly invoked. See issue sqlitebrowser#1332 and (tangentially) sqlitebrowser#1049. The first should be fixed now. The later not, but at least there is now a workaround: removing the AUTOINCREMENT option and use the WITHOUT ROWID one. * Problems with WITHOUT ROWID tables with PK of string type (alternative 2) Update after review: - cached_row is not modified after unlock(); - Alternative solution to initial key value insertion: When a new record is inserted and the PK has string type we still make a pseudo auto-increment and insert that value as a string literal. In this way we can later update that row. When we inserted it as integer an actual integer will be inserted by SQLite, and our UPDATE clause, which always uses string in the WHERE condition, won't match the row (SQLite does not convert to integer when the column is of type string in this context). See issue sqlitebrowser#1332.
1 parent e930b20 commit 66ffa5f

File tree

3 files changed

+12
-3
lines changed

3 files changed

+12
-3
lines changed

src/MainWindow.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -775,6 +775,7 @@ void MainWindow::closeEvent( QCloseEvent* event )
775775
void MainWindow::addRecord()
776776
{
777777
int row = m_browseTableModel->rowCount();
778+
778779
if(m_browseTableModel->insertRow(row))
779780
{
780781
selectTableLine(row);

src/sqlitedb.cpp

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1099,12 +1099,13 @@ QString DBBrowserDB::emptyInsertStmt(const QString& schemaName, const sqlb::Tabl
10991099

11001100
if(!pk_value.isNull())
11011101
{
1102-
vals << pk_value;
1102+
vals << (f.isText()? "'" + pk_value + "'" : pk_value);
11031103
} else {
11041104
if(f.notnull())
11051105
{
11061106
QString maxval = this->max(sqlb::ObjectIdentifier(schemaName, t.name()), f);
1107-
vals << QString::number(maxval.toLongLong() + 1);
1107+
QString newval = QString::number(maxval.toLongLong() + 1);
1108+
vals << (f.isText()? "'" + newval + "'" : newval);
11081109
} else {
11091110
vals << "NULL";
11101111
}

src/sqlitetablemodel.cpp

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -392,7 +392,14 @@ bool SqliteTableModel::setTypedData(const QModelIndex& index, bool isBlob, const
392392
if(m_db.updateRecord(m_sTable, m_headers.at(index.column()), cached_row.at(0), newValue, isBlob, m_pseudoPk))
393393
{
394394
cached_row.replace(index.column(), newValue);
395-
lock.unlock();
395+
if(m_headers.at(index.column()) == m_sRowidColumn) {
396+
cached_row.replace(0, newValue);
397+
const QModelIndex& rowidIndex = index.sibling(index.row(), 0);
398+
lock.unlock();
399+
emit dataChanged(rowidIndex, rowidIndex);
400+
} else {
401+
lock.unlock();
402+
}
396403
emit dataChanged(index, index);
397404
return true;
398405
} else {

0 commit comments

Comments
 (0)