Mybatis中Order By 不能使用#号

mybatis中使用#号可以防止SQL注入,但是order by却不能使用#而必须使用$,这是为什么呢?

测试环境:

CREATE TABLE `t2` (
	`id` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT,
	`value` VARCHAR(50) NULL DEFAULT '0',
	PRIMARY KEY (`id`)
)
ENGINE=InnoDB
;
mysql> select * from t2;
+----+-------+
| id | value |
+----+-------+
|  1 | 5     |
|  2 | 4     |
|  3 | 3     |
|  4 | 2     |
|  5 | 1     |
+----+-------+

试问两条SQL是一样的么?

select * from t2 order by value;
select * from t2 order by 'value';

先看现象:

mysql> select * from t2 order by value;
+----+-------+
| id | value |
+----+-------+
|  5 | 1     |
|  4 | 2     |
|  3 | 3     |
|  2 | 4     |
|  1 | 5     |
+----+-------+
mysql> select * from t2 order by 'value';
+----+-------+
| id | value |
+----+-------+
|  1 | 5     |
|  2 | 4     |
|  3 | 3     |
|  4 | 2     |
|  5 | 1     |
+----+-------+

可以看出当使用引号时,输出结果并没有排序。

这是因为当order by后是字符串,MySQL会认为根据一个常量列排序,例如:

mysql> select id,value,'value' from t2 order by 'value';
+----+-------+-------+
| id | value | value |
+----+-------+-------+
|  1 | 5     | value |
|  2 | 4     | value |
|  3 | 3     | value |
|  4 | 2     | value |
|  5 | 1     | value |
+----+-------+-------+

而常量列所有值都相等,所以也就不会排序。

Mybatis中如果使用#符引用参数,会自动在参数值两端加引号,导致排序失效,因此Mybatis中使用Order By时一定使用$符号!因为使用错误也不会报错,因此可能不容易发现。

另外如果表名是参数,也要用$符,因为表名不允许使用引号,直接就会报语法错误。


版权声明:本文为zhouwenjun0820原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。