Changeset 561 for trunk/src/sql/drivers/odbc
- Timestamp:
- Feb 11, 2010, 11:19:06 PM (15 years ago)
- Location:
- trunk
- Files:
-
- 3 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk
-
Property svn:mergeinfo
set to (toggle deleted branches)
/branches/vendor/nokia/qt/4.6.1 merged eligible /branches/vendor/nokia/qt/current merged eligible /branches/vendor/trolltech/qt/current 3-149
-
Property svn:mergeinfo
set to (toggle deleted branches)
-
trunk/src/sql/drivers/odbc/qsql_odbc.cpp
r2 r561 2 2 ** 3 3 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies). 4 ** Contact: Qt Software Information (qt-info@nokia.com) 4 ** All rights reserved. 5 ** Contact: Nokia Corporation (qt-info@nokia.com) 5 6 ** 6 7 ** This file is part of the QtSql module of the Qt Toolkit. … … 21 22 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. 22 23 ** 23 ** In addition, as a special exception, Nokia gives you certain 24 ** additional rights. These rights are described in the Nokia Qt LGPL 25 ** Exception version 1.0, included in the file LGPL_EXCEPTION.txt in this 26 ** package. 24 ** In addition, as a special exception, Nokia gives you certain additional 25 ** rights. These rights are described in the Nokia Qt LGPL Exception 26 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. 27 27 ** 28 28 ** GNU General Public License Usage … … 34 34 ** met: http://www.gnu.org/copyleft/gpl.html. 35 35 ** 36 ** If you are unsure which license is appropriate for your use, please37 ** contact the sales department at qt-sales@nokia.com.36 ** If you have questions regarding the use of this file, please contact 37 ** Nokia at qt-info@nokia.com. 38 38 ** $QT_END_LICENSE$ 39 39 ** … … 56 56 #include <qvector.h> 57 57 #include <QDebug> 58 #include <QSqlQuery> 58 59 59 60 QT_BEGIN_NAMESPACE … … 70 71 71 72 // newer platform SDKs use SQLLEN instead of SQLINTEGER 72 #if defined(SQLLEN) || defined(Q_OS_WIN64) 73 #if defined(WIN32) && (_MSC_VER < 1300) 74 # define QSQLLEN SQLINTEGER 75 # define QSQLULEN SQLUINTEGER 76 #else 73 77 # define QSQLLEN SQLLEN 74 #else75 # define QSQLLEN SQLINTEGER76 #endif77 78 #if defined(SQLULEN) || defined(Q_OS_WIN64)79 78 # define QSQLULEN SQLULEN 80 #else 81 # define QSQLULEN SQLUINTEGER 82 #endif 79 #endif 80 83 81 84 82 static const int COLNAMESIZE = 256; … … 89 87 { 90 88 public: 89 enum DefaultCase{Lower, Mixed, Upper, Sensitive}; 91 90 QODBCDriverPrivate() 92 91 : hEnv(0), hDbc(0), useSchema(false), disconnectCount(0), isMySqlServer(false), 93 isMSSqlServer(false), hasSQLFetchScroll(true), hasMultiResultSets(false) 92 isMSSqlServer(false), hasSQLFetchScroll(true), hasMultiResultSets(false), 93 isQuoteInitialized(false), quote(QLatin1Char('"')) 94 94 { 95 sql_char_type = sql_varchar_type = sql_longvarchar_type = QVariant::ByteArray;96 95 unicode = false; 97 96 } … … 102 101 uint unicode :1; 103 102 uint useSchema :1; 104 QVariant::Type sql_char_type;105 QVariant::Type sql_varchar_type;106 QVariant::Type sql_longvarchar_type;107 103 int disconnectCount; 108 104 bool isMySqlServer; … … 120 116 void splitTableQualifier(const QString &qualifier, QString &catalog, 121 117 QString &schema, QString &table); 118 DefaultCase defaultCase() const; 119 QString adjustCase(const QString&) const; 120 QChar quoteChar(); 121 private: 122 bool isQuoteInitialized; 123 QChar quote; 122 124 }; 123 125 … … 125 127 { 126 128 public: 127 QODBCPrivate( )128 : h Env(0), hDbc(0), hStmt(0), useSchema(false), hasSQLFetchScroll(true), precisionPolicy(QSql::HighPrecision)129 QODBCPrivate(QODBCDriverPrivate *dpp) 130 : hStmt(0), useSchema(false), hasSQLFetchScroll(true), driverPrivate(dpp), userForwardOnly(false) 129 131 { 130 sql_char_type = sql_varchar_type = sql_longvarchar_type = QVariant::ByteArray;131 132 unicode = false; 132 133 } … … 135 136 { fieldCache.fill(QVariant()); fieldCacheIdx = 0; } 136 137 137 SQLHANDLE hEnv;138 SQLHANDLE hDbc;138 SQLHANDLE dpEnv() const { return driverPrivate ? driverPrivate->hEnv : 0;} 139 SQLHANDLE dpDbc() const { return driverPrivate ? driverPrivate->hDbc : 0;} 139 140 SQLHANDLE hStmt; 140 141 141 142 uint unicode :1; 142 143 uint useSchema :1; 143 QVariant::Type sql_char_type;144 QVariant::Type sql_varchar_type;145 QVariant::Type sql_longvarchar_type;146 144 147 145 QSqlRecord rInf; … … 150 148 int disconnectCount; 151 149 bool hasSQLFetchScroll; 152 QSql::NumericalPrecisionPolicy precisionPolicy; 150 QODBCDriverPrivate *driverPrivate; 151 bool userForwardOnly; 153 152 154 153 bool isStmtHandleValid(const QSqlDriver *driver); … … 174 173 SQLRETURN r = SQL_NO_DATA; 175 174 SQLTCHAR state_[SQL_SQLSTATE_SIZE+1]; 176 SQLTCHAR description_[SQL_MAX_MESSAGE_LENGTH];175 QVarLengthArray<SQLTCHAR> description_(SQL_MAX_MESSAGE_LENGTH); 177 176 QString result; 178 177 int i = 1; 179 178 180 179 description_[0] = 0; 180 r = SQLGetDiagRec(handleType, 181 handle, 182 i, 183 state_, 184 &nativeCode_, 185 0, 186 NULL, 187 &msgLen); 188 if(r == SQL_NO_DATA) 189 return QString(); 190 description_.resize(msgLen+1); 181 191 do { 182 192 r = SQLGetDiagRec(handleType, 183 193 handle, 184 194 i, 185 (SQLTCHAR*)state_,195 state_, 186 196 &nativeCode_, 187 (SQLTCHAR*)description_,188 SQL_MAX_MESSAGE_LENGTH, /* in bytes, not in characters */197 description_.data(), 198 description_.size(), 189 199 &msgLen); 190 200 if (r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO) { … … 193 203 QString tmpstore; 194 204 #ifdef UNICODE 195 tmpstore = QString((const QChar*)description_ , msgLen);205 tmpstore = QString((const QChar*)description_.data(), msgLen); 196 206 #else 197 tmpstore = QString::fromLocal8Bit((const char*)description_ , msgLen);207 tmpstore = QString::fromLocal8Bit((const char*)description_.data(), msgLen); 198 208 #endif 199 209 if(result != tmpstore) { … … 212 222 static QString qODBCWarn(const QODBCPrivate* odbc, int *nativeCode = 0) 213 223 { 214 return (qWarnODBCHandle(SQL_HANDLE_ENV, odbc-> hEnv) + QLatin1String(" ")215 + qWarnODBCHandle(SQL_HANDLE_DBC, odbc-> hDbc) + QLatin1String(" ")224 return (qWarnODBCHandle(SQL_HANDLE_ENV, odbc->dpEnv()) + QLatin1Char(' ') 225 + qWarnODBCHandle(SQL_HANDLE_DBC, odbc->dpDbc()) + QLatin1Char(' ') 216 226 + qWarnODBCHandle(SQL_HANDLE_STMT, odbc->hStmt, nativeCode)); 217 227 } … … 219 229 static QString qODBCWarn(const QODBCDriverPrivate* odbc, int *nativeCode = 0) 220 230 { 221 return (qWarnODBCHandle(SQL_HANDLE_ENV, odbc->hEnv) + QLatin1 String(" ")231 return (qWarnODBCHandle(SQL_HANDLE_ENV, odbc->hEnv) + QLatin1Char(' ') 222 232 + qWarnODBCHandle(SQL_HANDLE_DBC, odbc->hDbc, nativeCode)); 223 233 } … … 251 261 static QVariant::Type qDecodeODBCType(SQLSMALLINT sqltype, const T* p, bool isSigned = true) 252 262 { 263 Q_UNUSED(p); 253 264 QVariant::Type type = QVariant::Invalid; 254 265 switch (sqltype) { … … 263 274 case SQL_INTEGER: 264 275 case SQL_BIT: 276 type = isSigned ? QVariant::Int : QVariant::UInt; 277 break; 265 278 case SQL_TINYINT: 266 type = isSigned ? QVariant::Int :QVariant::UInt;279 type = QVariant::UInt; 267 280 break; 268 281 case SQL_BIGINT: … … 294 307 #endif 295 308 case SQL_CHAR: 296 type = p->sql_char_type;297 break;298 309 case SQL_VARCHAR: 299 310 case SQL_GUID: 300 type = p->sql_varchar_type;301 break;302 311 case SQL_LONGVARCHAR: 303 type = p->sql_longvarchar_type;312 type = QVariant::String; 304 313 break; 305 314 default: … … 327 336 } 328 337 } 329 char* buf = new char[colSize];338 QVarLengthArray<char> buf(colSize); 330 339 while (true) { 331 340 r = SQLGetData(hStmt, 332 341 column+1, 333 342 unicode ? SQL_C_WCHAR : SQL_C_CHAR, 334 (SQLPOINTER)buf ,343 (SQLPOINTER)buf.data(), 335 344 colSize, 336 345 &lengthIndicator); … … 347 356 int rSize = (r == SQL_SUCCESS_WITH_INFO) ? (unicode ? colSize-2 : colSize-1) : lengthIndicator; 348 357 if (unicode) { 349 fieldVal += QString(( QChar*) buf, rSize / 2);358 fieldVal += QString((const QChar*) buf.constData(), rSize / 2); 350 359 } else { 351 fieldVal += QString::fromAscii(buf , rSize);360 fieldVal += QString::fromAscii(buf.constData(), rSize); 352 361 } 353 if (fieldVal.size() + lengthIndicator >= colSize) { 362 memset(buf.data(), 0, colSize); 363 if (lengthIndicator < colSize) { 354 364 // workaround for Drivermanagers that don't return SQL_NO_DATA 355 365 break; … … 363 373 } 364 374 } 365 delete[] buf;366 375 return fieldVal; 367 376 } … … 443 452 } 444 453 454 static QVariant qGetDoubleData(SQLHANDLE hStmt, int column) 455 { 456 SQLDOUBLE dblbuf; 457 QSQLLEN lengthIndicator = 0; 458 SQLRETURN r = SQLGetData(hStmt, 459 column+1, 460 SQL_C_DOUBLE, 461 (SQLPOINTER) &dblbuf, 462 0, 463 &lengthIndicator); 464 if (r != SQL_SUCCESS && r != SQL_SUCCESS_WITH_INFO) { 465 return QVariant(QVariant::Invalid); 466 } 467 if(lengthIndicator == SQL_NULL_DATA) 468 return QVariant(QVariant::Double); 469 470 return (double) dblbuf; 471 } 472 473 445 474 static QVariant qGetBigIntData(SQLHANDLE hStmt, int column, bool isSigned = true) 446 475 { … … 552 581 if (connOpts.contains(QLatin1String("SQL_ATTR_ODBC_VERSION=SQL_OV_ODBC3"), Qt::CaseInsensitive)) 553 582 return SQL_OV_ODBC3; 554 #endif 583 #endif 555 584 return SQL_OV_ODBC2; 556 585 } 586 587 QChar QODBCDriverPrivate::quoteChar() 588 { 589 if (!isQuoteInitialized) { 590 char driverResponse[4]; 591 SQLSMALLINT length; 592 int r = SQLGetInfo(hDbc, 593 SQL_IDENTIFIER_QUOTE_CHAR, 594 &driverResponse, 595 sizeof(driverResponse), 596 &length); 597 if (r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO) { 598 quote = QLatin1Char(driverResponse[0]); 599 } else { 600 quote = QLatin1Char('"'); 601 } 602 isQuoteInitialized = true; 603 } 604 return quote; 605 } 606 557 607 558 608 bool QODBCDriverPrivate::setConnectionOptions(const QString& connOpts) … … 706 756 } 707 757 758 QODBCDriverPrivate::DefaultCase QODBCDriverPrivate::defaultCase() const 759 { 760 DefaultCase ret; 761 SQLUSMALLINT casing; 762 int r = SQLGetInfo(hDbc, 763 SQL_IDENTIFIER_CASE, 764 &casing, 765 sizeof(casing), 766 NULL); 767 if ( r != SQL_SUCCESS) 768 ret = Mixed;//arbitrary case if driver cannot be queried 769 else { 770 switch (casing) { 771 case (SQL_IC_UPPER): 772 ret = Upper; 773 break; 774 case (SQL_IC_LOWER): 775 ret = Lower; 776 break; 777 case (SQL_IC_SENSITIVE): 778 ret = Sensitive; 779 break; 780 case (SQL_IC_MIXED): 781 default: 782 ret = Mixed; 783 break; 784 } 785 } 786 return ret; 787 } 788 789 /* 790 Adjust the casing of an identifier to match what the 791 database engine would have done to it. 792 */ 793 QString QODBCDriverPrivate::adjustCase(const QString &identifier) const 794 { 795 QString ret = identifier; 796 switch(defaultCase()) { 797 case (Lower): 798 ret = identifier.toLower(); 799 break; 800 case (Upper): 801 ret = identifier.toUpper(); 802 break; 803 case(Mixed): 804 case(Sensitive): 805 default: 806 ret = identifier; 807 } 808 return ret; 809 } 810 708 811 //////////////////////////////////////////////////////////////////////////// 709 812 … … 711 814 : QSqlResult(db) 712 815 { 713 d = new QODBCPrivate(); 714 d->hEnv = p->hEnv; 715 d->hDbc = p->hDbc; 816 d = new QODBCPrivate(p); 716 817 d->unicode = p->unicode; 717 818 d->useSchema = p->useSchema; 718 d->sql_char_type = p->sql_char_type;719 d->sql_varchar_type = p->sql_varchar_type;720 d->sql_longvarchar_type = p->sql_longvarchar_type;721 819 d->disconnectCount = p->disconnectCount; 722 820 d->hasSQLFetchScroll = p->hasSQLFetchScroll; … … 754 852 } 755 853 r = SQLAllocHandle(SQL_HANDLE_STMT, 756 d-> hDbc,854 d->dpDbc(), 757 855 &d->hStmt); 758 856 if (r != SQL_SUCCESS) { … … 763 861 d->updateStmtHandleState(driver()); 764 862 765 if ( isForwardOnly()) {863 if (d->userForwardOnly) { 766 864 r = SQLSetStmtAttr(d->hStmt, 767 865 SQL_ATTR_CURSOR_TYPE, … … 796 894 return false; 797 895 } 896 897 SQLINTEGER isScrollable, bufferLength; 898 r = SQLGetStmtAttr(d->hStmt, SQL_ATTR_CURSOR_SCROLLABLE, &isScrollable, SQL_IS_INTEGER, &bufferLength); 899 if(r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO) 900 QSqlResult::setForwardOnly(isScrollable==SQL_NONSCROLLABLE); 798 901 799 902 SQLSMALLINT count; … … 883 986 SQL_FETCH_FIRST, 884 987 0); 885 if (r != SQL_SUCCESS) { 988 if (r != SQL_SUCCESS) { 886 989 if (r != SQL_NO_DATA) 887 990 setLastError(qMakeError(QCoreApplication::translate("QODBCResult", … … 902 1005 SQL_FETCH_PRIOR, 903 1006 0); 904 if (r != SQL_SUCCESS) { 1007 if (r != SQL_SUCCESS) { 905 1008 if (r != SQL_NO_DATA) 906 1009 setLastError(qMakeError(QCoreApplication::translate("QODBCResult", … … 933 1036 SQL_FETCH_LAST, 934 1037 0); 935 if (r != SQL_SUCCESS) { 1038 if (r != SQL_SUCCESS) { 936 1039 if (r != SQL_NO_DATA) 937 1040 setLastError(qMakeError(QCoreApplication::translate("QODBCResult", … … 1024 1127 break; 1025 1128 case QVariant::String: 1026 d->fieldCache[i] = qGetStringData(d->hStmt, i, info.length(), true);1129 d->fieldCache[i] = qGetStringData(d->hStmt, i, info.length(), d->unicode); 1027 1130 break; 1028 1131 case QVariant::Double: 1029 { 1030 QString value=qGetStringData(d->hStmt, i, info.length(), false); 1031 bool ok=false; 1032 switch(d->precisionPolicy) { 1033 case QSql::LowPrecisionInt32: 1034 d->fieldCache[i] = value.toInt(&ok); 1035 break; 1036 case QSql::LowPrecisionInt64: 1037 d->fieldCache[i] = value.toLongLong(&ok); 1038 break; 1039 case QSql::LowPrecisionDouble: 1040 d->fieldCache[i] = value.toDouble(&ok); 1041 break; 1042 case QSql::HighPrecision: 1043 default: 1044 d->fieldCache[i] = value; 1045 ok=true; 1046 break; 1047 } 1048 if(ok==false) 1049 d->fieldCache[i] = QVariant(); 1050 break; 1132 switch(numericalPrecisionPolicy()) { 1133 case QSql::LowPrecisionInt32: 1134 d->fieldCache[i] = qGetIntData(d->hStmt, i); 1135 break; 1136 case QSql::LowPrecisionInt64: 1137 d->fieldCache[i] = qGetBigIntData(d->hStmt, i); 1138 break; 1139 case QSql::LowPrecisionDouble: 1140 d->fieldCache[i] = qGetDoubleData(d->hStmt, i); 1141 break; 1142 case QSql::HighPrecision: 1143 d->fieldCache[i] = qGetStringData(d->hStmt, i, info.length(), false); 1144 break; 1051 1145 } 1146 break; 1052 1147 default: 1053 1148 d->fieldCache[i] = QVariant(qGetStringData(d->hStmt, i, info.length(), false)); … … 1103 1198 } 1104 1199 r = SQLAllocHandle(SQL_HANDLE_STMT, 1105 d-> hDbc,1200 d->dpDbc(), 1106 1201 &d->hStmt); 1107 1202 if (r != SQL_SUCCESS) { … … 1112 1207 d->updateStmtHandleState(driver()); 1113 1208 1114 if ( isForwardOnly()) {1209 if (d->userForwardOnly) { 1115 1210 r = SQLSetStmtAttr(d->hStmt, 1116 1211 SQL_ATTR_CURSOR_TYPE, … … 1372 1467 #endif 1373 1468 { 1374 QByteArray str = val.toString().to Utf8();1469 QByteArray str = val.toString().toAscii(); 1375 1470 if (*ind != SQL_NULL_DATA) 1376 1471 *ind = str.length(); 1377 1472 int strSize = str.length(); 1378 1473 1379 1474 r = SQLBindParameter(d->hStmt, 1380 1475 i + 1, … … 1423 1518 } 1424 1519 1520 SQLINTEGER isScrollable, bufferLength; 1521 r = SQLGetStmtAttr(d->hStmt, SQL_ATTR_CURSOR_SCROLLABLE, &isScrollable, SQL_IS_INTEGER, &bufferLength); 1522 if(r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO) 1523 QSqlResult::setForwardOnly(isScrollable==SQL_NONSCROLLABLE); 1524 1425 1525 SQLSMALLINT count; 1426 1526 SQLNumResultCols(d->hStmt, &count); … … 1457 1557 QTime(dt.hour, dt.minute, dt.second, dt.fraction / 1000000))); 1458 1558 break; } 1559 case QVariant::Bool: 1459 1560 case QVariant::Int: 1460 1561 case QVariant::UInt: … … 1546 1647 *static_cast<bool*>(data) = nextResult(); 1547 1648 break; 1548 case QSqlResult::SetNumericalPrecision:1549 Q_ASSERT(data);1550 d->precisionPolicy = *reinterpret_cast<QSql::NumericalPrecisionPolicy *>(data);1551 break;1552 1649 default: 1553 1650 QSqlResult::virtual_hook(id, data); 1554 1651 } 1652 } 1653 1654 void QODBCResult::setForwardOnly(bool forward) 1655 { 1656 d->userForwardOnly = forward; 1657 QSqlResult::setForwardOnly(forward); 1555 1658 } 1556 1659 … … 1670 1773 if (db.contains(QLatin1String(".dsn"), Qt::CaseInsensitive)) 1671 1774 connQStr = QLatin1String("FILEDSN=") + db; 1672 else if (db.contains(QLatin1String("DRIVER="), Qt::CaseInsensitive) 1775 else if (db.contains(QLatin1String("DRIVER="), Qt::CaseInsensitive) 1673 1776 || db.contains(QLatin1String("SERVER="), Qt::CaseInsensitive)) 1674 1777 connQStr = db; … … 1680 1783 if (!password.isEmpty()) 1681 1784 connQStr += QLatin1String(";PWD=") + password; 1682 1785 1683 1786 SQLSMALLINT cb; 1684 1787 SQLTCHAR connOut[1024]; … … 1703 1806 if (!d->checkDriver()) { 1704 1807 setLastError(qMakeError(tr("Unable to connect - Driver doesn't support all " 1705 " needed functionality"), QSqlError::ConnectionError, d));1808 "functionality required"), QSqlError::ConnectionError, d)); 1706 1809 setOpenError(true); 1707 1810 return false; … … 1715 1818 setOpen(true); 1716 1819 setOpenError(false); 1820 if(d->isMSSqlServer) { 1821 QSqlQuery i(createResult()); 1822 i.exec(QLatin1String("SET QUOTED_IDENTIFIER ON")); 1823 } 1717 1824 return true; 1718 1825 } … … 1763 1870 return; 1764 1871 #endif 1765 #if defined(Q_WS_WIN) 1766 QT_WA( 1767 {}, 1768 { 1769 unicode = false; 1770 return; 1771 }) 1772 #endif 1872 1773 1873 SQLRETURN r; 1774 1874 SQLUINTEGER fFunc; … … 1781 1881 NULL); 1782 1882 if ((r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO) && (fFunc & SQL_CVT_WCHAR)) { 1783 sql_char_type = QVariant::String;1784 1883 unicode = true; 1785 1884 } … … 1791 1890 NULL); 1792 1891 if ((r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO) && (fFunc & SQL_CVT_WVARCHAR)) { 1793 sql_varchar_type = QVariant::String;1794 1892 unicode = true; 1795 1893 } … … 1801 1899 NULL); 1802 1900 if ((r == SQL_SUCCESS || r == SQL_SUCCESS_WITH_INFO) && (fFunc & SQL_CVT_WLONGVARCHAR)) { 1803 sql_longvarchar_type = QVariant::String;1804 1901 unicode = true; 1805 1902 } … … 2085 2182 QString catalog, schema, table; 2086 2183 d->splitTableQualifier(tablename, catalog, schema, table); 2184 2185 if (isIdentifierEscaped(catalog, QSqlDriver::TableName)) 2186 catalog = stripDelimiters(catalog, QSqlDriver::TableName); 2187 else 2188 catalog = d->adjustCase(catalog); 2189 2190 if (isIdentifierEscaped(schema, QSqlDriver::TableName)) 2191 schema = stripDelimiters(schema, QSqlDriver::TableName); 2192 else 2193 schema = d->adjustCase(schema); 2194 2195 if (isIdentifierEscaped(table, QSqlDriver::TableName)) 2196 table = stripDelimiters(table, QSqlDriver::TableName); 2197 else 2198 table = d->adjustCase(table); 2199 2087 2200 r = SQLSetStmtAttr(hStmt, 2088 2201 SQL_ATTR_CURSOR_TYPE, … … 2187 2300 QString catalog, schema, table; 2188 2301 d->splitTableQualifier(tablename, catalog, schema, table); 2302 2303 if (isIdentifierEscaped(catalog, QSqlDriver::TableName)) 2304 catalog = stripDelimiters(catalog, QSqlDriver::TableName); 2305 else 2306 catalog = d->adjustCase(catalog); 2307 2308 if (isIdentifierEscaped(schema, QSqlDriver::TableName)) 2309 schema = stripDelimiters(schema, QSqlDriver::TableName); 2310 else 2311 schema = d->adjustCase(schema); 2312 2313 if (isIdentifierEscaped(table, QSqlDriver::TableName)) 2314 table = stripDelimiters(table, QSqlDriver::TableName); 2315 else 2316 table = d->adjustCase(table); 2317 2189 2318 SQLRETURN r = SQLAllocHandle(SQL_HANDLE_STMT, 2190 2319 d->hDbc, … … 2294 2423 QString QODBCDriver::escapeIdentifier(const QString &identifier, IdentifierType) const 2295 2424 { 2425 QChar quote = d->quoteChar(); 2296 2426 QString res = identifier; 2297 if (d->isMySqlServer) { 2298 if(!identifier.isEmpty() && identifier.left(1) != QString(QLatin1Char('`')) && identifier.right(1) != QString(QLatin1Char('`')) ) { 2299 res.prepend(QLatin1Char('`')).append(QLatin1Char('`')); 2300 res.replace(QLatin1Char('.'), QLatin1String("`.`")); 2301 } 2302 } else { 2303 if(!identifier.isEmpty() && identifier.left(1) != QString(QLatin1Char('"')) && identifier.right(1) != QString(QLatin1Char('"')) ) { 2304 res.replace(QLatin1Char('"'), QLatin1String("\"\"")); 2305 res.prepend(QLatin1Char('"')).append(QLatin1Char('"')); 2306 res.replace(QLatin1Char('.'), QLatin1String("\".\"")); 2307 } 2427 if(!identifier.isEmpty() && !identifier.startsWith(quote) && !identifier.endsWith(quote) ) { 2428 res.replace(quote, QString(quote)+QString(quote)); 2429 res.prepend(quote).append(quote); 2430 res.replace(QLatin1Char('.'), QString(quote)+QLatin1Char('.')+QString(quote)); 2308 2431 } 2309 2432 return res; 2310 2433 } 2311 2434 2435 bool QODBCDriver::isIdentifierEscapedImplementation(const QString &identifier, IdentifierType) const 2436 { 2437 QChar quote = d->quoteChar(); 2438 return identifier.size() > 2 2439 && identifier.startsWith(quote) //left delimited 2440 && identifier.endsWith(quote); //right delimited 2441 } 2442 2312 2443 QT_END_NAMESPACE -
trunk/src/sql/drivers/odbc/qsql_odbc.h
r2 r561 2 2 ** 3 3 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies). 4 ** Contact: Qt Software Information (qt-info@nokia.com) 4 ** All rights reserved. 5 ** Contact: Nokia Corporation (qt-info@nokia.com) 5 6 ** 6 7 ** This file is part of the QtSql module of the Qt Toolkit. … … 21 22 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. 22 23 ** 23 ** In addition, as a special exception, Nokia gives you certain 24 ** additional rights. These rights are described in the Nokia Qt LGPL 25 ** Exception version 1.0, included in the file LGPL_EXCEPTION.txt in this 26 ** package. 24 ** In addition, as a special exception, Nokia gives you certain additional 25 ** rights. These rights are described in the Nokia Qt LGPL Exception 26 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. 27 27 ** 28 28 ** GNU General Public License Usage … … 34 34 ** met: http://www.gnu.org/copyleft/gpl.html. 35 35 ** 36 ** If you are unsure which license is appropriate for your use, please37 ** contact the sales department at qt-sales@nokia.com.36 ** If you have questions regarding the use of this file, please contact 37 ** Nokia at qt-info@nokia.com. 38 38 ** $QT_END_LICENSE$ 39 39 ** … … 101 101 102 102 QVariant handle() const; 103 virtual void setForwardOnly(bool forward); 103 104 104 105 protected: … … 146 147 QString escapeIdentifier(const QString &identifier, IdentifierType type) const; 147 148 149 protected Q_SLOTS: 150 bool isIdentifierEscapedImplementation(const QString &identifier, IdentifierType type) const; 151 148 152 protected: 149 153 bool beginTransaction(); 150 154 bool commitTransaction(); 151 155 bool rollbackTransaction(); 156 152 157 private: 153 158 void init();
Note:
See TracChangeset
for help on using the changeset viewer.