mybatis的#{}和${}的区别以及order by注入问题
前言略,直奔主题..
#{}相当于jdbc中的preparedstatement
${}是输出变量的值
你可能说不明所以,不要紧我们看2段代码:
String sql = "select * from admin_domain_location order by ?";
PreparedStatement st = con.prepareStatement(sql);
st.setString(1, "domain_id");
System.out.println(st.toString());
ResultSet rs = st.executeQuery();
while(rs.next()){
System.out.println(rs.getString("domain_id"));
}
输出结果:
com.mysql.jdbc.PreparedStatement@1fa1ba1: select * from admin_domain_location order by 'domain_id'
3
4
5
2
6
这是个jdbc的preparedstatement例子,不要吐槽我这么写是否合法,这里只是为了说明问题.
以上例子有得出以下信息:
1)order by后面如果采用预编译的形式动态输入参数,那么实际插入的参数是一个字符串,例子中是:order by 'domain_id'
2)输出结果并没有排序,从sql语句中的形式我们也可以推测出此sql语句根本也不合法(正常应该是 order by domain_id)
修改以上代码如下:
String input = "domain_id";
String sql = "select * from admin_domain_location order by "+input;
PreparedStatement st = con.prepareStatement(sql);
System.out.println(st.toString());
ResultSet rs = st.executeQuery();
while(rs.next()){
System.out.println(rs.getString("domain_id"));
}
输出结果:
com.mysql.jdbc.PreparedStatement@1fa1ba1: select * from admin_domain_location order by domain_id
2
3
4
5
6
此次我们直接把一个变量的值拼接sql语句,从结果可以看出来:
1)sql语句拼接正常
2)查询结果排序正常
你可能要问这和#{}与${}有什么关系..
上面已经说过#{}相当于jdbc的preparedstatement,所以以上的第一个例子就相当于#{},那么第二个例子就自然而然指的是${}的情况.
你可能说思维还是有些凌乱,不要紧我们来看第三个例子:
String sql = "select * from admin_domain_location where domain_id=?";
PreparedStatement st = con.prepareStatement(sql);
st.setString(1, "2");
System.out.println(st.toString());
ResultSet rs = st.executeQuery();
while(rs.next()){
System.out.println(rs.getString("domain_id"));
}
=======================================
String input = "2";
String sql = "select * from admin_domain_location where domain_id='"+input+"'";
PreparedStatement st = con.prepareStatement(sql);
System.out.println(st.toString());
ResultSet rs = st.executeQuery();
while(rs.next()){
System.out.println(rs.getString("domain_id"));
} 输出结果都为:
com.mysql.jdbc.PreparedStatement@12bf560: select * from admin_domain_location where domain_id='2'
2
这第三个例子说的是#{}和${}通用的问题,也就是说在此种情况下#{}和${}是通用的,只不过需要些小的转换.如例子中需要手动
拼接单引号 ' ' 到变量值的前后,确保sql语句正常.
简单说#{}是经过预编译的,是安全的,而${}是未经过预编译的,仅仅是取变量的值,是非安全的,存在sql注入.
这里先说一下只能${}的情况,从我们前面的例子中也能看出,order by是肯定只能用${}了,用#{}会多个' '导致sql语句失效.此外还有一个like 语句后也需要用${},简单想一下
就能明白.由于${}仅仅是简单的取值,所以以前sql注入的方法适用此处,如果我们order by语句后用了${},那么不做任何处理的时候是存在sql注入危险的.你说怎么防止,那我只
能悲惨的告诉你,你得手动处理过滤一下输入的内容,如判断一下输入的参数的长度是否正常(注入语句一般很长),更精确的过滤则可以查询一下输入的参数是否在预期的参数集合中..
mybatis的#{}和${}的区别以及order by注入问题的更多相关文章
- mybatis中#{}和${}的区别及order by的sql注入问题
mybatis的#{}和${}的区别以及order by注入问题 原文 http://www.cnblogs.com/chyu/p/4389701.html 前言略,直奔主题.. #{}相当于j ...
- MyBatis中#{ }和${ }的区别,数据库优化遵循层次和查询方法
MyBatis中#{ }和${ }的区别详解 1.#将传入的数据当成一个字符串,会对自动传入的数据加一个 双引号. 例如order by #id#,如果传入的值是111,那么解析成sql时变为orde ...
- mybatis中的#{}和${}区别
mybatis中的#{}和${}区别 2017年05月19日 13:59:24 阅读数:16165 1. #将传入的数据都当成一个字符串,会对自动传入的数据加一个双引号.如:order by #use ...
- Mybatis笔记八:MyBatis中#{}和${}的区别
先给大家介绍下MyBatis中#{}和${}的区别,具体介绍如下: 1. $将传入的数据直接显示生成在sql中 2. #方式能够很大程度防止sql注入. 3.$方式无法防止Sql注入. 4.$方式一般 ...
- Mybatis与Ibatis的区别
Mybatis与Ibatis的区别: 1.Mybatis实现了接口绑定,使用更加方便 在ibatis2.x中我们需要在DAO的实现类中指定具体对应哪个xml映射文件, 而Mybatis实现了DAO接口 ...
- mybatis与hibernate的区别持久层对比【面试题】
Mybatis技术特点: 好处: 通过直接编写SQL语句,可以直接对SQL进行性能的优化: 学习门槛低,学习成本低.只要有SQL基础,就可以学习mybatis,而且很容易上手: 由于直接编写SQL语句 ...
- JavaWeb_(Mybatis框架)JDBC操作数据库和Mybatis框架操作数据库区别_一
系列博文: JavaWeb_(Mybatis框架)JDBC操作数据库和Mybatis框架操作数据库区别_一 传送门 JavaWeb_(Mybatis框架)使用Mybatis对表进行增.删.改.查操作_ ...
- 【ORM】Mybatis与JPA的区别
Mybatis与JPA的区别: 1.ORM映射不同: Mybatis是半自动的ORM框架,提供数据库与结果集的映射: JPA(Hibernate)是全自动的ORM框架,提供对象与数据库的映射: 2.可 ...
- order by 注入姿势
order by 注入原理 其实orde by 注入也是sql注入的一种,原理都一样就是mysql语法的区别,order by是用来排序的语法. sql-lab讲解 判断方法 1.通过做运算来判断如: ...
随机推荐
- {"集合已修改;可能无法执行枚举操作。"}
无论是向集合中添加元素还是从集合中删除元素,都会导致集合内部的变化,特别是集合遍历器的变化.例如 List<,,,,}; foreach(int x in list) { list.Remove ...
- 你可以做一个更好的Coder为了自己的将来
小小的星辰 工作已经一年多了,时间真的好快啊!发现自己还是终于走出了当初的阴影!我可以快乐的做我自己了.这两年发现自己改变了很多!很庆幸,我可以不想你了!伤感的心情总会过去的.还记得曾经说过一句:“离 ...
- mysql学习笔记 第九天
order by ,limit 和where子查询的使用 order by: order by 列名1,[列名2],[列名3]...(结果先按列1进行排序,在列1的相同的情况下,再按照列2的排序,以此 ...
- 容器--ArrayList
一.前言 作为List的重要实现之一,ArrayList已经成了我们编写程序时不可或缺的重要容器之一,面试的时候也经常会被问到,所以,深入理解其实现机制,无论是对于我们正确使用这个类来说,还是准备面试 ...
- java事务理解
还在学Hibernate,后续一大堆概念刚接触需要理解.觉得-——事务——这个概念不是很好理解,所以发上来记录一下. 首先说点千篇一律的东西.概念和特性都是随处可见的,无论哪里都很容易找到,关键是你如 ...
- Android:TextView 自动滚动(跑马灯) (转)
Android:TextView 自动滚动(跑马灯) TextView实现文字滚动需要以下几个要点: 1.文字长度长于可显示范围:android:singleLine="true ...
- 2013 最新的 play web framework 版本 1.2.3 框架学习文档整理
Play framework框架学习文档 Play framework框架学习文档 1 一.什么是Playframework 3 二.playframework框架的优点 4 三.Play Frame ...
- mustache模板渲染的基本原理
mustache.js是一个模板引擎,为开发节省了大量的“人力”,对于初学者,我是从这篇 和这篇 博客接触的,算是对mustache有了初步认识,不得不承认自己还是菜鸟阶段还有太多东西要学,慢慢熟悉. ...
- 回车键和button按钮都绑定同一个事件,如何避免按回车的时候button重复点击
保存一个全局变量,用来记录Button的焦点状态 <button onclick="login();" onfocus="window.buttonIsFocuse ...
- SAP debug的几种方式
1. 直接在程序中设断点 这种方式想必大家都知道了,在se38里面打上breakpoint,程序运行到该处即进入debug模式 2.background Job的debug 进入SM37 ...