Adding extra lesson for order by clauses
This commit is contained in:
@ -0,0 +1,48 @@
|
||||
== Order by clause
|
||||
|
||||
Question: Does a preparared statement always prevent against an SQL injection?
|
||||
Answer: No it does not
|
||||
|
||||
Let's take a look at the following statement:
|
||||
|
||||
----
|
||||
select * from users order by lastname;
|
||||
----
|
||||
|
||||
If we look at the specification of the SQL grammar the definition is as follows:
|
||||
|
||||
----
|
||||
SELECT ...
|
||||
FROM tableList
|
||||
[WHERE Expression]
|
||||
[ORDER BY orderExpression [, ...]]
|
||||
|
||||
orderExpression:
|
||||
{ columnNr | columnAlias | selectExpression }
|
||||
[ASC | DESC]
|
||||
|
||||
selectExpression:
|
||||
{ Expression | COUNT(*) | {
|
||||
COUNT | MIN | MAX | SUM | AVG | SOME | EVERY |
|
||||
VAR_POP | VAR_SAMP | STDDEV_POP | STDDEV_SAMP
|
||||
} ([ALL | DISTINCT][2]] Expression) } [[AS] label]
|
||||
|
||||
Based on HSQLDB
|
||||
----
|
||||
|
||||
This means an `orderExpression` van be a `selectExpression` which can be a function as well, so for example with
|
||||
a `case` statement we might be able to ask the database some questions, like:
|
||||
|
||||
----
|
||||
select * from users order by
|
||||
(select case when (true) then lastname else firstname)
|
||||
----
|
||||
|
||||
So we can substitute any kind of boolean operation in the `when(....)` part. The statement will just work because
|
||||
it is a valid query whether you use a prepared statement or not an order by clause can by definition contain a
|
||||
expression.
|
||||
|
||||
=== Mitigation
|
||||
|
||||
If you need to provide a sorting column in your web application you should implement a whitelist to validate the value
|
||||
of the `order by` statement it should always be limited to something like 'firstname' or 'lastname'.
|
Reference in New Issue
Block a user