mirror of
https://github.com/qgis/QGIS.git
synced 2025-03-04 00:30:59 -05:00
Unify sqlite string quoting functions to a single QgsSqliteUtils::quoteString
function, with tests
This commit is contained in:
parent
7e81226b51
commit
ed35ad9ca7
@ -141,7 +141,7 @@ bool QgsCustomProjectionDialog::deleteCrs( const QString &id )
|
||||
{
|
||||
sqlite3_database_unique_ptr database;
|
||||
|
||||
QString sql = "delete from tbl_srs where srs_id=" + quotedValue( id );
|
||||
QString sql = "delete from tbl_srs where srs_id=" + QgsSqliteUtils::quotedString( id );
|
||||
QgsDebugMsg( sql );
|
||||
//check the db is available
|
||||
int result = database.open( QgsApplication::qgisUserDatabaseFilePath() );
|
||||
@ -191,7 +191,7 @@ void QgsCustomProjectionDialog::insertProjection( const QString &projectionAcro
|
||||
else
|
||||
{
|
||||
// Set up the query to retrieve the projection information needed to populate the PROJECTION list
|
||||
QString srsSql = "select acronym,name,notes,parameters from tbl_projection where acronym=" + quotedValue( projectionAcronym );
|
||||
QString srsSql = "select acronym,name,notes,parameters from tbl_projection where acronym=" + QgsSqliteUtils::quotedString( projectionAcronym );
|
||||
|
||||
sqlite3_statement_unique_ptr srsPreparedStatement = srsDatabase.prepare( srsSql, srsResult );
|
||||
if ( srsResult == SQLITE_OK )
|
||||
@ -201,10 +201,10 @@ void QgsCustomProjectionDialog::insertProjection( const QString &projectionAcro
|
||||
QgsDebugMsg( "Trying to insert projection" );
|
||||
// We have the result from system srs.db. Now insert into user db.
|
||||
sql = "insert into tbl_projection(acronym,name,notes,parameters) values ("
|
||||
+ quotedValue( srsPreparedStatement.columnAsText( 0 ) )
|
||||
+ ',' + quotedValue( srsPreparedStatement.columnAsText( 1 ) )
|
||||
+ ',' + quotedValue( srsPreparedStatement.columnAsText( 2 ) )
|
||||
+ ',' + quotedValue( srsPreparedStatement.columnAsText( 3 ) )
|
||||
+ QgsSqliteUtils::quotedString( srsPreparedStatement.columnAsText( 0 ) )
|
||||
+ ',' + QgsSqliteUtils::quotedString( srsPreparedStatement.columnAsText( 1 ) )
|
||||
+ ',' + QgsSqliteUtils::quotedString( srsPreparedStatement.columnAsText( 2 ) )
|
||||
+ ',' + QgsSqliteUtils::quotedString( srsPreparedStatement.columnAsText( 3 ) )
|
||||
+ ')';
|
||||
sqlite3_statement_unique_ptr preparedStatement = database.prepare( sql, result );
|
||||
if ( result != SQLITE_OK || preparedStatement.step() != SQLITE_DONE )
|
||||
@ -239,12 +239,12 @@ bool QgsCustomProjectionDialog::saveCrs( QgsCoordinateReferenceSystem parameters
|
||||
else
|
||||
{
|
||||
sql = "update tbl_srs set description="
|
||||
+ quotedValue( name )
|
||||
+ ",projection_acronym=" + quotedValue( projectionAcronym )
|
||||
+ ",ellipsoid_acronym=" + quotedValue( ellipsoidAcronym )
|
||||
+ ",parameters=" + quotedValue( parameters.toProj4() )
|
||||
+ QgsSqliteUtils::quotedString( name )
|
||||
+ ",projection_acronym=" + QgsSqliteUtils::quotedString( projectionAcronym )
|
||||
+ ",ellipsoid_acronym=" + QgsSqliteUtils::quotedString( ellipsoidAcronym )
|
||||
+ ",parameters=" + QgsSqliteUtils::quotedString( parameters.toProj4() )
|
||||
+ ",is_geo=0" // <--shamelessly hard coded for now
|
||||
+ " where srs_id=" + quotedValue( id )
|
||||
+ " where srs_id=" + QgsSqliteUtils::quotedString( id )
|
||||
;
|
||||
QgsDebugMsg( sql );
|
||||
sqlite3_database_unique_ptr database;
|
||||
@ -521,12 +521,6 @@ void QgsCustomProjectionDialog::pbnCalculate_clicked()
|
||||
pj_ctx_free( pContext );
|
||||
}
|
||||
|
||||
QString QgsCustomProjectionDialog::quotedValue( QString value )
|
||||
{
|
||||
value.replace( '\'', QLatin1String( "''" ) );
|
||||
return value.prepend( '\'' ).append( '\'' );
|
||||
}
|
||||
|
||||
void QgsCustomProjectionDialog::showHelp()
|
||||
{
|
||||
QgsHelp::openHelp( QStringLiteral( "working_with_projections/working_with_projections.html" ) );
|
||||
|
@ -50,7 +50,6 @@ class APP_EXPORT QgsCustomProjectionDialog : public QDialog, private Ui::QgsCust
|
||||
|
||||
//helper functions
|
||||
void populateList();
|
||||
QString quotedValue( QString value );
|
||||
bool deleteCrs( const QString &id );
|
||||
bool saveCrs( QgsCoordinateReferenceSystem parameters, const QString &name, const QString &id, bool newEntry );
|
||||
void insertProjection( const QString &projectionAcronym );
|
||||
|
@ -421,11 +421,11 @@ bool QgsNewSpatialiteLayerDialog::apply()
|
||||
if ( mGeometryTypeBox->currentIndex() != 0 )
|
||||
{
|
||||
QString sqlAddGeom = QStringLiteral( "select AddGeometryColumn(%1,%2,%3,%4,%5)" )
|
||||
.arg( quotedValue( leLayerName->text() ),
|
||||
quotedValue( leGeometryColumn->text() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( leLayerName->text() ),
|
||||
QgsSqliteUtils::quotedString( leGeometryColumn->text() ) )
|
||||
.arg( mCrsId.split( ':' ).value( 1, QStringLiteral( "0" ) ).toInt() )
|
||||
.arg( quotedValue( selectedType() ) )
|
||||
.arg( quotedValue( selectedZM() ) );
|
||||
.arg( QgsSqliteUtils::quotedString( selectedType() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( selectedZM() ) );
|
||||
QgsDebugMsg( sqlAddGeom );
|
||||
|
||||
rc = sqlite3_exec( database.get(), sqlAddGeom.toUtf8(), nullptr, nullptr, &errmsg );
|
||||
@ -439,8 +439,8 @@ bool QgsNewSpatialiteLayerDialog::apply()
|
||||
}
|
||||
|
||||
QString sqlCreateIndex = QStringLiteral( "select CreateSpatialIndex(%1,%2)" )
|
||||
.arg( quotedValue( leLayerName->text() ),
|
||||
quotedValue( leGeometryColumn->text() ) );
|
||||
.arg( QgsSqliteUtils::quotedString( leLayerName->text() ),
|
||||
QgsSqliteUtils::quotedString( leGeometryColumn->text() ) );
|
||||
QgsDebugMsg( sqlCreateIndex );
|
||||
|
||||
rc = sqlite3_exec( database.get(), sqlCreateIndex.toUtf8(), nullptr, nullptr, &errmsg );
|
||||
@ -488,12 +488,6 @@ QString QgsNewSpatialiteLayerDialog::quotedIdentifier( QString id )
|
||||
return id.prepend( '\"' ).append( '\"' );
|
||||
}
|
||||
|
||||
QString QgsNewSpatialiteLayerDialog::quotedValue( QString value )
|
||||
{
|
||||
value.replace( '\'', QLatin1String( "''" ) );
|
||||
return value.prepend( '\'' ).append( '\'' );
|
||||
}
|
||||
|
||||
void QgsNewSpatialiteLayerDialog::showHelp()
|
||||
{
|
||||
QgsHelp::openHelp( QStringLiteral( "managing_data_source/create_layers.html#creating-a-new-spatialite-layer" ) );
|
||||
|
@ -66,7 +66,6 @@ class APP_EXPORT QgsNewSpatialiteLayerDialog: public QDialog, private Ui::QgsNew
|
||||
void showHelp();
|
||||
|
||||
static QString quotedIdentifier( QString id );
|
||||
static QString quotedValue( QString value );
|
||||
|
||||
QPushButton *mOkButton = nullptr;
|
||||
QString mCrsId;
|
||||
|
@ -498,7 +498,7 @@ bool QgsCoordinateReferenceSystem::loadFromDatabase( const QString &db, const QS
|
||||
|
||||
QString mySql = "select srs_id,description,projection_acronym,"
|
||||
"ellipsoid_acronym,parameters,srid,auth_name||':'||auth_id,is_geo "
|
||||
"from tbl_srs where " + expression + '=' + quotedValue( value ) + " order by deprecated";
|
||||
"from tbl_srs where " + expression + '=' + QgsSqliteUtils::quotedString( value ) + " order by deprecated";
|
||||
statement = database.prepare( mySql, myResult );
|
||||
// XXX Need to free memory from the error msg if one is set
|
||||
if ( myResult == SQLITE_OK && statement.step() == SQLITE_ROW )
|
||||
@ -729,7 +729,7 @@ bool QgsCoordinateReferenceSystem::createFromProj4( const QString &proj4String )
|
||||
* We try to match the proj string to and srsid using the following logic:
|
||||
* - perform a whole text search on proj4 string (if not null)
|
||||
*/
|
||||
myRecord = getRecord( "select * from tbl_srs where parameters=" + quotedValue( myProj4String ) + " order by deprecated" );
|
||||
myRecord = getRecord( "select * from tbl_srs where parameters=" + QgsSqliteUtils::quotedString( myProj4String ) + " order by deprecated" );
|
||||
if ( myRecord.empty() )
|
||||
{
|
||||
// Ticket #722 - aaronr
|
||||
@ -764,7 +764,7 @@ bool QgsCoordinateReferenceSystem::createFromProj4( const QString &proj4String )
|
||||
myStart2 = myLat2RegExp.indexIn( proj4String, myStart2 );
|
||||
proj4StringModified.replace( myStart2 + LAT_PREFIX_LEN, myLength2 - LAT_PREFIX_LEN, lat1Str );
|
||||
QgsDebugMsgLevel( "trying proj4string match with swapped lat_1,lat_2", 4 );
|
||||
myRecord = getRecord( "select * from tbl_srs where parameters=" + quotedValue( proj4StringModified.trimmed() ) + " order by deprecated" );
|
||||
myRecord = getRecord( "select * from tbl_srs where parameters=" + QgsSqliteUtils::quotedString( proj4StringModified.trimmed() ) + " order by deprecated" );
|
||||
}
|
||||
}
|
||||
|
||||
@ -785,7 +785,7 @@ bool QgsCoordinateReferenceSystem::createFromProj4( const QString &proj4String )
|
||||
QStringList myParams;
|
||||
Q_FOREACH ( const QString ¶m, myProj4String.split( QRegExp( "\\s+(?=\\+)" ), QString::SkipEmptyParts ) )
|
||||
{
|
||||
QString arg = QStringLiteral( "' '||parameters||' ' LIKE %1" ).arg( quotedValue( QStringLiteral( "% %1 %" ).arg( param.trimmed() ) ) );
|
||||
QString arg = QStringLiteral( "' '||parameters||' ' LIKE %1" ).arg( QgsSqliteUtils::quotedString( QStringLiteral( "% %1 %" ).arg( param.trimmed() ) ) );
|
||||
if ( param.startsWith( QLatin1String( "+datum=" ) ) )
|
||||
{
|
||||
datum = arg;
|
||||
@ -1234,8 +1234,8 @@ long QgsCoordinateReferenceSystem::findMatchingProj()
|
||||
// needed to populate the list
|
||||
QString mySql = QString( "select srs_id,parameters from tbl_srs where "
|
||||
"projection_acronym=%1 and ellipsoid_acronym=%2 order by deprecated" )
|
||||
.arg( quotedValue( d->mProjectionAcronym ),
|
||||
quotedValue( d->mEllipsoidAcronym ) );
|
||||
.arg( QgsSqliteUtils::quotedString( d->mProjectionAcronym ),
|
||||
QgsSqliteUtils::quotedString( d->mEllipsoidAcronym ) );
|
||||
// Get the full path name to the sqlite3 spatial reference database.
|
||||
QString myDatabaseFileName = QgsApplication::srsDatabaseFilePath();
|
||||
|
||||
@ -1620,19 +1620,19 @@ long QgsCoordinateReferenceSystem::saveAsUserCrs( const QString &name )
|
||||
{
|
||||
mySql = "insert into tbl_srs (srs_id,description,projection_acronym,ellipsoid_acronym,parameters,is_geo) values ("
|
||||
+ QString::number( USER_CRS_START_ID )
|
||||
+ ',' + quotedValue( name )
|
||||
+ ',' + quotedValue( projectionAcronym() )
|
||||
+ ',' + quotedValue( ellipsoidAcronym() )
|
||||
+ ',' + quotedValue( toProj4() )
|
||||
+ ',' + QgsSqliteUtils::quotedString( name )
|
||||
+ ',' + QgsSqliteUtils::quotedString( projectionAcronym() )
|
||||
+ ',' + QgsSqliteUtils::quotedString( ellipsoidAcronym() )
|
||||
+ ',' + QgsSqliteUtils::quotedString( toProj4() )
|
||||
+ ",0)"; // <-- is_geo shamelessly hard coded for now
|
||||
}
|
||||
else
|
||||
{
|
||||
mySql = "insert into tbl_srs (description,projection_acronym,ellipsoid_acronym,parameters,is_geo) values ("
|
||||
+ quotedValue( name )
|
||||
+ ',' + quotedValue( projectionAcronym() )
|
||||
+ ',' + quotedValue( ellipsoidAcronym() )
|
||||
+ ',' + quotedValue( toProj4() )
|
||||
+ QgsSqliteUtils::quotedString( name )
|
||||
+ ',' + QgsSqliteUtils::quotedString( projectionAcronym() )
|
||||
+ ',' + QgsSqliteUtils::quotedString( ellipsoidAcronym() )
|
||||
+ ',' + QgsSqliteUtils::quotedString( toProj4() )
|
||||
+ ",0)"; // <-- is_geo shamelessly hard coded for now
|
||||
}
|
||||
sqlite3_database_unique_ptr database;
|
||||
@ -1707,12 +1707,6 @@ long QgsCoordinateReferenceSystem::getRecordCount()
|
||||
return myRecordCount;
|
||||
}
|
||||
|
||||
QString QgsCoordinateReferenceSystem::quotedValue( QString value )
|
||||
{
|
||||
value.replace( '\'', QLatin1String( "''" ) );
|
||||
return value.prepend( '\'' ).append( '\'' );
|
||||
}
|
||||
|
||||
// adapted from gdal/ogr/ogr_srs_dict.cpp
|
||||
bool QgsCoordinateReferenceSystem::loadWkts( QHash<int, QString> &wkts, const char *filename )
|
||||
{
|
||||
@ -1951,8 +1945,8 @@ int QgsCoordinateReferenceSystem::syncDatabase()
|
||||
{
|
||||
errMsg = nullptr;
|
||||
sql = QStringLiteral( "UPDATE tbl_srs SET parameters=%1,description=%2,deprecated=%3 WHERE auth_name='EPSG' AND auth_id=%4" )
|
||||
.arg( quotedValue( proj4 ) )
|
||||
.arg( quotedValue( name ) )
|
||||
.arg( QgsSqliteUtils::quotedString( proj4 ) )
|
||||
.arg( QgsSqliteUtils::quotedString( name ) )
|
||||
.arg( deprecated ? 1 : 0 )
|
||||
.arg( it.key() );
|
||||
|
||||
@ -1989,10 +1983,10 @@ int QgsCoordinateReferenceSystem::syncDatabase()
|
||||
}
|
||||
|
||||
sql = QStringLiteral( "INSERT INTO tbl_srs(description,projection_acronym,ellipsoid_acronym,parameters,srid,auth_name,auth_id,is_geo,deprecated) VALUES (%1,%2,%3,%4,%5,'EPSG',%5,%6,%7)" )
|
||||
.arg( quotedValue( name ),
|
||||
quotedValue( projRegExp.cap( 1 ) ),
|
||||
quotedValue( ellps ),
|
||||
quotedValue( proj4 ) )
|
||||
.arg( QgsSqliteUtils::quotedString( name ),
|
||||
QgsSqliteUtils::quotedString( projRegExp.cap( 1 ) ),
|
||||
QgsSqliteUtils::quotedString( ellps ),
|
||||
QgsSqliteUtils::quotedString( proj4 ) )
|
||||
.arg( it.key() )
|
||||
.arg( OSRIsGeographic( crs ) )
|
||||
.arg( deprecated ? 1 : 0 );
|
||||
@ -2081,9 +2075,9 @@ int QgsCoordinateReferenceSystem::syncDatabase()
|
||||
if ( proj4 != params )
|
||||
{
|
||||
sql = QStringLiteral( "UPDATE tbl_srs SET parameters=%1 WHERE auth_name=%2 AND auth_id=%3" )
|
||||
.arg( quotedValue( proj4 ),
|
||||
quotedValue( auth_name ),
|
||||
quotedValue( auth_id ) );
|
||||
.arg( QgsSqliteUtils::quotedString( proj4 ),
|
||||
QgsSqliteUtils::quotedString( auth_name ),
|
||||
QgsSqliteUtils::quotedString( auth_id ) );
|
||||
|
||||
if ( sqlite3_exec( database.get(), sql.toUtf8(), nullptr, nullptr, &errMsg ) == SQLITE_OK )
|
||||
{
|
||||
@ -2291,7 +2285,7 @@ bool QgsCoordinateReferenceSystem::syncDatumTransform( const QString &dbPath )
|
||||
int idx = map[i].idx;
|
||||
Q_ASSERT( idx != -1 );
|
||||
Q_ASSERT( idx < n );
|
||||
v.insert( i, *values[ idx ] ? quotedValue( values[idx] ) : QStringLiteral( "NULL" ) );
|
||||
v.insert( i, *values[ idx ] ? QgsSqliteUtils::quotedString( values[idx] ) : QStringLiteral( "NULL" ) );
|
||||
}
|
||||
CSLDestroy( values );
|
||||
|
||||
|
@ -741,9 +741,6 @@ class CORE_EXPORT QgsCoordinateReferenceSystem
|
||||
//! Helper for getting number of user CRS already in db
|
||||
long getRecordCount();
|
||||
|
||||
//! Helper for sql-safe value quoting
|
||||
static QString quotedValue( QString value );
|
||||
|
||||
/**
|
||||
* Initialize the CRS object by looking up CRS database in path given in db argument,
|
||||
* using first CRS entry where expression = 'value'
|
||||
|
@ -91,6 +91,16 @@ sqlite3_statement_unique_ptr sqlite3_database_unique_ptr::prepare( const QString
|
||||
return s;
|
||||
}
|
||||
|
||||
QString QgsSqliteUtils::quotedString( const QString &value )
|
||||
{
|
||||
if ( value.isNull() )
|
||||
return QStringLiteral( "NULL" );
|
||||
|
||||
QString v = value;
|
||||
v.replace( '\'', QLatin1String( "''" ) );
|
||||
return v.prepend( '\'' ).append( '\'' );
|
||||
}
|
||||
|
||||
QString QgsSqlite3Mprintf( const char *format, ... )
|
||||
{
|
||||
va_list ap;
|
||||
|
@ -135,8 +135,24 @@ class CORE_EXPORT sqlite3_database_unique_ptr : public std::unique_ptr< sqlite3,
|
||||
* argument will be filled with the sqlite3 result code.
|
||||
*/
|
||||
sqlite3_statement_unique_ptr prepare( const QString &sql, int &resultCode ) const;
|
||||
|
||||
};
|
||||
|
||||
/**
|
||||
* Contains utilities for working with Sqlite data sources.
|
||||
* \note not available in Python bindings
|
||||
* \since QGIS 3.4
|
||||
*/
|
||||
class CORE_EXPORT QgsSqliteUtils
|
||||
{
|
||||
public:
|
||||
|
||||
/**
|
||||
* Returns a quoted string \a value, surround by ' characters and with special
|
||||
* characters correctly escaped.
|
||||
*/
|
||||
static QString quotedString( const QString &value );
|
||||
};
|
||||
|
||||
/**
|
||||
* Wraps sqlite3_mprintf() by automatically freeing the memory.
|
||||
|
@ -454,15 +454,6 @@ error:
|
||||
return false;
|
||||
}
|
||||
|
||||
QString QgsSpatiaLiteConnection::quotedValue( QString value ) const
|
||||
{
|
||||
if ( value.isNull() )
|
||||
return QStringLiteral( "NULL" );
|
||||
|
||||
value.replace( '\'', QLatin1String( "''" ) );
|
||||
return value.prepend( '\'' ).append( '\'' );
|
||||
}
|
||||
|
||||
bool QgsSpatiaLiteConnection::checkGeometryColumnsAuth( sqlite3 *handle )
|
||||
{
|
||||
int ret;
|
||||
@ -624,8 +615,8 @@ bool QgsSpatiaLiteConnection::isDeclaredHidden( sqlite3 *handle, const QString &
|
||||
return false;
|
||||
// checking if some Layer has been declared as HIDDEN
|
||||
QString sql = QString( "SELECT hidden FROM geometry_columns_auth"
|
||||
" WHERE f_table_name=%1 and f_geometry_column=%2" ).arg( quotedValue( table ),
|
||||
quotedValue( geom ) );
|
||||
" WHERE f_table_name=%1 and f_geometry_column=%2" ).arg( QgsSqliteUtils::quotedString( table ),
|
||||
QgsSqliteUtils::quotedString( geom ) );
|
||||
|
||||
ret = sqlite3_get_table( handle, sql.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( ret != SQLITE_OK )
|
||||
|
@ -104,9 +104,6 @@ class QgsSpatiaLiteConnection : public QObject
|
||||
*/
|
||||
bool getTableInfoAbstractInterface( sqlite3 *handle, bool loadGeometrylessTables );
|
||||
|
||||
//! Cleaning well-formatted SQL strings
|
||||
QString quotedValue( QString value ) const;
|
||||
|
||||
//! Checks if geometry_columns_auth table exists
|
||||
bool checkGeometryColumnsAuth( sqlite3 *handle );
|
||||
|
||||
|
@ -229,7 +229,7 @@ QgsSpatiaLiteProvider::createEmptyLayer( const QString &uri,
|
||||
throw SLException( errMsg );
|
||||
|
||||
sql = QStringLiteral( "DELETE FROM geometry_columns WHERE upper(f_table_name) = upper(%1)" )
|
||||
.arg( quotedValue( tableName ) );
|
||||
.arg( QgsSqliteUtils::quotedString( tableName ) );
|
||||
|
||||
ret = sqlite3_exec( sqliteHandle, sql.toUtf8().constData(), nullptr, nullptr, &errMsg );
|
||||
if ( ret != SQLITE_OK )
|
||||
@ -308,10 +308,10 @@ QgsSpatiaLiteProvider::createEmptyLayer( const QString &uri,
|
||||
if ( !geometryType.isEmpty() )
|
||||
{
|
||||
sql = QStringLiteral( "SELECT AddGeometryColumn(%1, %2, %3, %4, %5)" )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( tableName ),
|
||||
QgsSpatiaLiteProvider::quotedValue( geometryColumn ) )
|
||||
.arg( QgsSqliteUtils::quotedString( tableName ),
|
||||
QgsSqliteUtils::quotedString( geometryColumn ) )
|
||||
.arg( srid )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( geometryType ) )
|
||||
.arg( QgsSqliteUtils::quotedString( geometryType ) )
|
||||
.arg( dim );
|
||||
|
||||
ret = sqlite3_exec( sqliteHandle, sql.toUtf8().constData(), nullptr, nullptr, &errMsg );
|
||||
@ -820,7 +820,7 @@ QString QgsSpatiaLiteProvider::tableSchemaCondition( const QgsDataSourceUri &dsU
|
||||
{
|
||||
return dsUri.schema().isEmpty() ?
|
||||
QStringLiteral( "IS NULL" ) :
|
||||
QStringLiteral( "= %1" ).arg( quotedValue( dsUri.schema( ) ) );
|
||||
QStringLiteral( "= %1" ).arg( QgsSqliteUtils::quotedString( dsUri.schema( ) ) );
|
||||
}
|
||||
|
||||
void QgsSpatiaLiteProvider::fetchConstraints()
|
||||
@ -1102,8 +1102,8 @@ void QgsSpatiaLiteProvider::determineViewPrimaryKey()
|
||||
{
|
||||
QString sql = QString( "SELECT view_rowid"
|
||||
" FROM views_geometry_columns"
|
||||
" WHERE upper(view_name) = upper(%1) and upper(view_geometry) = upper(%2)" ).arg( quotedValue( mTableName ),
|
||||
quotedValue( mGeometryColumn ) );
|
||||
" WHERE upper(view_name) = upper(%1) and upper(view_geometry) = upper(%2)" ).arg( QgsSqliteUtils::quotedString( mTableName ),
|
||||
QgsSqliteUtils::quotedString( mGeometryColumn ) );
|
||||
|
||||
char **results = nullptr;
|
||||
int rows;
|
||||
@ -4322,12 +4322,12 @@ bool QgsSpatiaLiteProvider::changeAttributeValues( const QgsChangedAttributesMap
|
||||
else if ( type == QVariant::StringList || type == QVariant::List )
|
||||
{
|
||||
// binding an array value
|
||||
sql += QStringLiteral( "%1=%2" ).arg( quotedIdentifier( fld.name() ), quotedValue( QgsJsonUtils::encodeValue( val ) ) );
|
||||
sql += QStringLiteral( "%1=%2" ).arg( quotedIdentifier( fld.name() ), QgsSqliteUtils::quotedString( QgsJsonUtils::encodeValue( val ) ) );
|
||||
}
|
||||
else
|
||||
{
|
||||
// binding a TEXT value
|
||||
sql += QStringLiteral( "%1=%2" ).arg( quotedIdentifier( fld.name() ), quotedValue( val.toString() ) );
|
||||
sql += QStringLiteral( "%1=%2" ).arg( quotedIdentifier( fld.name() ), QgsSqliteUtils::quotedString( val.toString() ) );
|
||||
}
|
||||
}
|
||||
catch ( SLFieldNotFound )
|
||||
@ -4465,15 +4465,6 @@ QString QgsSpatiaLiteProvider::quotedIdentifier( QString id )
|
||||
return id.prepend( '\"' ).append( '\"' );
|
||||
}
|
||||
|
||||
QString QgsSpatiaLiteProvider::quotedValue( QString value )
|
||||
{
|
||||
if ( value.isNull() )
|
||||
return QStringLiteral( "NULL" );
|
||||
|
||||
value.replace( '\'', QLatin1String( "''" ) );
|
||||
return value.prepend( '\'' ).append( '\'' );
|
||||
}
|
||||
|
||||
bool QgsSpatiaLiteProvider::checkLayerTypeAbstractInterface( gaiaVectorLayerPtr lyr )
|
||||
{
|
||||
if ( !lyr )
|
||||
@ -4538,7 +4529,7 @@ bool QgsSpatiaLiteProvider::checkLayerType()
|
||||
// checking if is a non-spatial table
|
||||
sql = QString( "SELECT type FROM sqlite_master "
|
||||
"WHERE lower(name) = lower(%1) "
|
||||
"AND type in ('table', 'view') " ).arg( quotedValue( mTableName ) );
|
||||
"AND type in ('table', 'view') " ).arg( QgsSqliteUtils::quotedString( mTableName ) );
|
||||
|
||||
ret = sqlite3_get_table( mSqliteHandle, sql.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( ret == SQLITE_OK && rows == 1 )
|
||||
@ -4652,8 +4643,8 @@ bool QgsSpatiaLiteProvider::checkLayerType()
|
||||
"LEFT JOIN geometry_columns_auth "
|
||||
"USING (f_table_name, f_geometry_column) "
|
||||
"WHERE upper(f_table_name) = upper(%1) and upper(f_geometry_column) = upper(%2)" )
|
||||
.arg( quotedValue( mTableName ),
|
||||
quotedValue( mGeometryColumn ) );
|
||||
.arg( QgsSqliteUtils::quotedString( mTableName ),
|
||||
QgsSqliteUtils::quotedString( mGeometryColumn ) );
|
||||
|
||||
ret = sqlite3_get_table( mSqliteHandle, sql.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( ret != SQLITE_OK )
|
||||
@ -4662,8 +4653,8 @@ bool QgsSpatiaLiteProvider::checkLayerType()
|
||||
{
|
||||
sqlite3_free( errMsg );
|
||||
sql = QStringLiteral( "SELECT 0 FROM geometry_columns WHERE upper(f_table_name) = upper(%1) and upper(f_geometry_column) = upper(%2)" )
|
||||
.arg( quotedValue( mTableName ),
|
||||
quotedValue( mGeometryColumn ) );
|
||||
.arg( QgsSqliteUtils::quotedString( mTableName ),
|
||||
QgsSqliteUtils::quotedString( mGeometryColumn ) );
|
||||
ret = sqlite3_get_table( mSqliteHandle, sql.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
}
|
||||
}
|
||||
@ -4691,8 +4682,8 @@ bool QgsSpatiaLiteProvider::checkLayerType()
|
||||
|
||||
// checking if this one is a View-based layer
|
||||
sql = QString( "SELECT view_name, view_geometry FROM views_geometry_columns"
|
||||
" WHERE view_name=%1 and view_geometry=%2" ).arg( quotedValue( mTableName ),
|
||||
quotedValue( mGeometryColumn ) );
|
||||
" WHERE view_name=%1 and view_geometry=%2" ).arg( QgsSqliteUtils::quotedString( mTableName ),
|
||||
QgsSqliteUtils::quotedString( mGeometryColumn ) );
|
||||
|
||||
ret = sqlite3_get_table( mSqliteHandle, sql.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( ret == SQLITE_OK && rows == 1 )
|
||||
@ -4711,8 +4702,8 @@ bool QgsSpatiaLiteProvider::checkLayerType()
|
||||
|
||||
// checking if this one is a VirtualShapefile-based layer
|
||||
sql = QString( "SELECT virt_name, virt_geometry FROM virts_geometry_columns"
|
||||
" WHERE virt_name=%1 and virt_geometry=%2" ).arg( quotedValue( mTableName ),
|
||||
quotedValue( mGeometryColumn ) );
|
||||
" WHERE virt_name=%1 and virt_geometry=%2" ).arg( QgsSqliteUtils::quotedString( mTableName ),
|
||||
QgsSqliteUtils::quotedString( mGeometryColumn ) );
|
||||
|
||||
ret = sqlite3_get_table( mSqliteHandle, sql.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( ret == SQLITE_OK && rows == 1 )
|
||||
@ -4822,8 +4813,8 @@ void QgsSpatiaLiteProvider::getViewSpatialIndexName()
|
||||
|
||||
QString sql = QString( "SELECT f_table_name, f_geometry_column "
|
||||
"FROM views_geometry_columns "
|
||||
"WHERE upper(view_name) = upper(%1) and upper(view_geometry) = upper(%2)" ).arg( quotedValue( mTableName ),
|
||||
quotedValue( mGeometryColumn ) );
|
||||
"WHERE upper(view_name) = upper(%1) and upper(view_geometry) = upper(%2)" ).arg( QgsSqliteUtils::quotedString( mTableName ),
|
||||
QgsSqliteUtils::quotedString( mGeometryColumn ) );
|
||||
ret = sqlite3_get_table( mSqliteHandle, sql.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( ret != SQLITE_OK )
|
||||
{
|
||||
@ -4876,8 +4867,8 @@ bool QgsSpatiaLiteProvider::getTableGeometryDetails()
|
||||
mIndexGeometry = mGeometryColumn;
|
||||
|
||||
QString sql = QString( "SELECT type, srid, spatial_index_enabled, coord_dimension FROM geometry_columns"
|
||||
" WHERE upper(f_table_name) = upper(%1) and upper(f_geometry_column) = upper(%2)" ).arg( quotedValue( mTableName ),
|
||||
quotedValue( mGeometryColumn ) );
|
||||
" WHERE upper(f_table_name) = upper(%1) and upper(f_geometry_column) = upper(%2)" ).arg( QgsSqliteUtils::quotedString( mTableName ),
|
||||
QgsSqliteUtils::quotedString( mGeometryColumn ) );
|
||||
|
||||
ret = sqlite3_get_table( mSqliteHandle, sql.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( ret != SQLITE_OK )
|
||||
@ -4974,8 +4965,8 @@ bool QgsSpatiaLiteProvider::getViewGeometryDetails()
|
||||
QString sql = QString( "SELECT type, srid, spatial_index_enabled, f_table_name, f_geometry_column "
|
||||
" FROM views_geometry_columns"
|
||||
" JOIN geometry_columns USING (f_table_name, f_geometry_column)"
|
||||
" WHERE upper(view_name) = upper(%1) and upper(view_geometry) = upper(%2)" ).arg( quotedValue( mTableName ),
|
||||
quotedValue( mGeometryColumn ) );
|
||||
" WHERE upper(view_name) = upper(%1) and upper(view_geometry) = upper(%2)" ).arg( QgsSqliteUtils::quotedString( mTableName ),
|
||||
QgsSqliteUtils::quotedString( mGeometryColumn ) );
|
||||
|
||||
ret = sqlite3_get_table( mSqliteHandle, sql.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( ret != SQLITE_OK )
|
||||
@ -5052,8 +5043,8 @@ bool QgsSpatiaLiteProvider::getVShapeGeometryDetails()
|
||||
char *errMsg = nullptr;
|
||||
|
||||
QString sql = QString( "SELECT type, srid FROM virts_geometry_columns"
|
||||
" WHERE virt_name=%1 and virt_geometry=%2" ).arg( quotedValue( mTableName ),
|
||||
quotedValue( mGeometryColumn ) );
|
||||
" WHERE virt_name=%1 and virt_geometry=%2" ).arg( QgsSqliteUtils::quotedString( mTableName ),
|
||||
QgsSqliteUtils::quotedString( mGeometryColumn ) );
|
||||
|
||||
ret = sqlite3_get_table( mSqliteHandle, sql.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( ret != SQLITE_OK )
|
||||
@ -5692,7 +5683,7 @@ QGISEXTERN bool saveStyle( const QString &uri, const QString &qmlStyle, const QS
|
||||
if ( !uiFileContent.isEmpty() )
|
||||
{
|
||||
uiFileColumn = QStringLiteral( ",ui" );
|
||||
uiFileValue = QStringLiteral( ",%1" ).arg( QgsSpatiaLiteProvider::quotedValue( uiFileContent ) );
|
||||
uiFileValue = QStringLiteral( ",%1" ).arg( QgsSqliteUtils::quotedString( uiFileContent ) );
|
||||
}
|
||||
|
||||
QString sql = QString( "INSERT INTO layer_styles("
|
||||
@ -5700,16 +5691,16 @@ QGISEXTERN bool saveStyle( const QString &uri, const QString &qmlStyle, const QS
|
||||
") VALUES ("
|
||||
"%1,%2,%3,%4,%5,%6,%7,%8,%9,%10%12"
|
||||
")" )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( QString() ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.schema() ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.table() ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.geometryColumn() ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( styleName.isEmpty() ? dsUri.table() : styleName ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( qmlStyle ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( sldStyle ) )
|
||||
.arg( QgsSqliteUtils::quotedString( QString() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.schema() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.table() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.geometryColumn() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( styleName.isEmpty() ? dsUri.table() : styleName ) )
|
||||
.arg( QgsSqliteUtils::quotedString( qmlStyle ) )
|
||||
.arg( QgsSqliteUtils::quotedString( sldStyle ) )
|
||||
.arg( useAsDefault ? "1" : "0" )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( styleDescription.isEmpty() ? QDateTime::currentDateTime().toString() : styleDescription ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.username() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( styleDescription.isEmpty() ? QDateTime::currentDateTime().toString() : styleDescription ) )
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.username() ) )
|
||||
.arg( uiFileColumn )
|
||||
.arg( uiFileValue );
|
||||
|
||||
@ -5720,9 +5711,9 @@ QGISEXTERN bool saveStyle( const QString &uri, const QString &qmlStyle, const QS
|
||||
" AND f_geometry_column=%3"
|
||||
" AND styleName=%4" )
|
||||
.arg( QgsSpatiaLiteProvider::tableSchemaCondition( dsUri ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.table() ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.geometryColumn() ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( styleName.isEmpty() ? dsUri.table() : styleName ) );
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.table() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.geometryColumn() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( styleName.isEmpty() ? dsUri.table() : styleName ) );
|
||||
|
||||
ret = sqlite3_get_table( sqliteHandle, checkQuery.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( SQLITE_OK != ret )
|
||||
@ -5757,14 +5748,14 @@ QGISEXTERN bool saveStyle( const QString &uri, const QString &qmlStyle, const QS
|
||||
" AND f_geometry_column=%8"
|
||||
" AND styleName=%9" )
|
||||
.arg( useAsDefault ? "1" : "0" )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( qmlStyle ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( sldStyle ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( styleDescription.isEmpty() ? QDateTime::currentDateTime().toString() : styleDescription ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.username() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( qmlStyle ) )
|
||||
.arg( QgsSqliteUtils::quotedString( sldStyle ) )
|
||||
.arg( QgsSqliteUtils::quotedString( styleDescription.isEmpty() ? QDateTime::currentDateTime().toString() : styleDescription ) )
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.username() ) )
|
||||
.arg( QgsSpatiaLiteProvider::tableSchemaCondition( dsUri ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.table() ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.geometryColumn() ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( styleName.isEmpty() ? dsUri.table() : styleName ) );
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.table() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.geometryColumn() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( styleName.isEmpty() ? dsUri.table() : styleName ) );
|
||||
}
|
||||
|
||||
if ( useAsDefault )
|
||||
@ -5775,8 +5766,8 @@ QGISEXTERN bool saveStyle( const QString &uri, const QString &qmlStyle, const QS
|
||||
" AND f_table_name=%2"
|
||||
" AND f_geometry_column=%3" )
|
||||
.arg( QgsSpatiaLiteProvider::tableSchemaCondition( dsUri ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.table() ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.geometryColumn() ) );
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.table() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.geometryColumn() ) );
|
||||
sql = QStringLiteral( "BEGIN; %1; %2; COMMIT;" ).arg( removeDefaultSql, sql );
|
||||
}
|
||||
|
||||
@ -5821,7 +5812,7 @@ QGISEXTERN QString loadStyle( const QString &uri, QString &errCause )
|
||||
}
|
||||
else
|
||||
{
|
||||
geomColumnExpr = QStringLiteral( "=" ) + QgsSpatiaLiteProvider::quotedValue( dsUri.geometryColumn() );
|
||||
geomColumnExpr = QStringLiteral( "=" ) + QgsSqliteUtils::quotedString( dsUri.geometryColumn() );
|
||||
}
|
||||
|
||||
QString selectQmlQuery = QString( "SELECT styleQML"
|
||||
@ -5832,7 +5823,7 @@ QGISEXTERN QString loadStyle( const QString &uri, QString &errCause )
|
||||
" ORDER BY CASE WHEN useAsDefault THEN 1 ELSE 2 END"
|
||||
",update_time DESC LIMIT 1" )
|
||||
.arg( QgsSpatiaLiteProvider::tableSchemaCondition( dsUri ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.table() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.table() ) )
|
||||
.arg( geomColumnExpr );
|
||||
|
||||
char **results = nullptr;
|
||||
@ -5912,8 +5903,8 @@ QGISEXTERN int listStyles( const QString &uri, QStringList &ids, QStringList &na
|
||||
" AND f_geometry_column=%3"
|
||||
" ORDER BY useasdefault DESC, update_time DESC" )
|
||||
.arg( QgsSpatiaLiteProvider::tableSchemaCondition( dsUri ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.table() ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.geometryColumn() ) );
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.table() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.geometryColumn() ) );
|
||||
|
||||
ret = sqlite3_get_table( sqliteHandle, selectRelatedQuery.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( SQLITE_OK != ret )
|
||||
@ -5938,8 +5929,8 @@ QGISEXTERN int listStyles( const QString &uri, QStringList &ids, QStringList &na
|
||||
" WHERE NOT (f_table_schema %1 AND f_table_name=%2 AND f_geometry_column=%3)"
|
||||
" ORDER BY update_time DESC" )
|
||||
.arg( QgsSpatiaLiteProvider::tableSchemaCondition( dsUri ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.table() ) )
|
||||
.arg( QgsSpatiaLiteProvider::quotedValue( dsUri.geometryColumn() ) );
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.table() ) )
|
||||
.arg( QgsSqliteUtils::quotedString( dsUri.geometryColumn() ) );
|
||||
|
||||
ret = sqlite3_get_table( sqliteHandle, selectOthersQuery.toUtf8().constData(), &results, &rows, &columns, &errMsg );
|
||||
if ( SQLITE_OK != ret )
|
||||
@ -5980,7 +5971,7 @@ QGISEXTERN QString getStyleById( const QString &uri, QString styleId, QString &e
|
||||
sqlite3 *sqliteHandle = handle->handle();
|
||||
|
||||
QString style;
|
||||
QString selectQmlQuery = QStringLiteral( "SELECT styleQml FROM layer_styles WHERE id=%1" ).arg( QgsSpatiaLiteProvider::quotedValue( styleId ) );
|
||||
QString selectQmlQuery = QStringLiteral( "SELECT styleQml FROM layer_styles WHERE id=%1" ).arg( QgsSqliteUtils::quotedString( styleId ) );
|
||||
char **results = nullptr;
|
||||
int rows;
|
||||
int columns;
|
||||
|
@ -144,7 +144,6 @@ class QgsSpatiaLiteProvider: public QgsVectorDataProvider
|
||||
static int computeMultiWKB3Dsize( const unsigned char *p_in, int little_endian,
|
||||
int endian_arch );
|
||||
static QString quotedIdentifier( QString id );
|
||||
static QString quotedValue( QString value );
|
||||
|
||||
struct SLFieldNotFound {}; //! Exception to throw
|
||||
|
||||
|
@ -46,6 +46,8 @@ class TestQgsSqliteUtils : public QObject
|
||||
|
||||
void testPrintfAscii();
|
||||
void testPrintfUtf8();
|
||||
void testQuotedString_data();
|
||||
void testQuotedString();
|
||||
};
|
||||
|
||||
|
||||
@ -90,6 +92,24 @@ void TestQgsSqliteUtils::testPrintfUtf8()
|
||||
QCOMPARE( query, QString( "SELECT id FROM tag WHERE LOWER(name)='%1'" ).arg( lowerTag ) );
|
||||
}
|
||||
|
||||
void TestQgsSqliteUtils::testQuotedString_data()
|
||||
{
|
||||
QTest::addColumn<QString>( "input" );
|
||||
QTest::addColumn<QString>( "expected" );
|
||||
|
||||
QTest::newRow( "test 1" ) << "university of qgis" << "'university of qgis'";
|
||||
QTest::newRow( "test 2" ) << "university of 'qgis'" << "'university of ''qgis'''";
|
||||
QTest::newRow( "test NULL" ) << QString() << "NULL";
|
||||
}
|
||||
|
||||
void TestQgsSqliteUtils::testQuotedString()
|
||||
{
|
||||
QFETCH( QString, input );
|
||||
QFETCH( QString, expected );
|
||||
|
||||
QCOMPARE( QgsSqliteUtils::quotedString( input ), expected );
|
||||
}
|
||||
|
||||
|
||||
QGSTEST_MAIN( TestQgsSqliteUtils )
|
||||
#include "testqgssqliteutils.moc"
|
||||
|
Loading…
x
Reference in New Issue
Block a user