Skip to content

Commit 169eccb

Browse files
committed
SqliteTableModel: Remove comments from SQL queries
Remove any single line comments from the SQL queries to fix all those problems ocurring when a query ending with such a comment is inserted into the COUNT query. Executing the query SELECT * FROM table -- comment would otherwise lead to this one being executed as well SELECT COUNT(*) FROM (SELECT * FROM table -- comment); This is obviously invalid SQL and therefore returns no data, sometimes even crashing the application, even though the original statement by the user is perfectly fine. The code used in this commit is a bit of a workaround and should be replaced as soon as there is a more complete SQL parser supporting SQL comments in our grammar tools. Closes sqlitebrowser#31.
1 parent a98c96e commit 169eccb

File tree

1 file changed

+33
-1
lines changed

1 file changed

+33
-1
lines changed

src/sqlitetablemodel.cpp

Lines changed: 33 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,38 @@ QString rtrimChar(const QString& s, QChar c) {
4040
r.chop(1);
4141
return r;
4242
}
43+
44+
QString removeComments(QString s)
45+
{
46+
// Feel free to fix all the bugs this probably contains or just replace this function entirely by
47+
// a 'simple' regular expression. I know there're better ways to do this...
48+
49+
// This function removes any single line comments (starting with '--') from a given string. It does
50+
// so by going through the string character by character and trying to keep track of wether we currently
51+
// are in a string or identifier and only removing those parts starting with '--' which are in neither.
52+
53+
QChar lastChar = 0;
54+
QList<QChar> stringChars;
55+
for(int i=0;i<s.length();i++)
56+
{
57+
if(lastChar != '\\' && (s.at(i) == '\'' || s.at(i) == '"' || s.at(i) == '`'))
58+
{
59+
if(!stringChars.empty() && stringChars.last() == s.at(i))
60+
stringChars.removeLast();
61+
else if(!(!stringChars.empty() && (stringChars.last() != '\'' || stringChars.last() != '"')) || stringChars.empty())
62+
stringChars.push_back(s.at(i));
63+
} else if(stringChars.empty() && s.at(i) == '-' && lastChar == '-') {
64+
if(s.contains('\n'))
65+
return removeComments(s.remove(i-1, s.indexOf('\n', i)-i));
66+
else
67+
return s.left(i-1);
68+
}
69+
70+
lastChar = s.at(i);
71+
}
72+
73+
return s;
74+
}
4375
}
4476

4577
void SqliteTableModel::setQuery(const QString& sQuery, bool dontClearHeaders)
@@ -52,7 +84,7 @@ void SqliteTableModel::setQuery(const QString& sQuery, bool dontClearHeaders)
5284
if(!m_db->isOpen())
5385
return;
5486

55-
m_sQuery = sQuery.trimmed();
87+
m_sQuery = removeComments(sQuery).trimmed();
5688

5789
// do a count query to get the full row count in a fast manner
5890
m_rowCount = getQueryRowCount();

0 commit comments

Comments
 (0)