MyBatis中 #{} 和 ${} 的区别小结
在MyBatis中,#{}
和${}
是两种常见的占位符,它们的作用和使用场景有所不同。理解它们的区别对于正确使用MyBatis非常重要。
在Mybatis面试中常涉及到关于#{}和${}的区别
1、#{}是预编译处理,$ {}是字符串替换。
2、MyBatis在处理#{}时,会将SQL中的#{}替换为?号,使用PreparedStatement的set方法来赋值;MyBatis在处理 $ { } 时,就是把 ${ } 替换成变量的值。
3、使用 #{} 可以有效的防止SQL注入,提高系统安全性。
1. #{} 和 ${} 的基本区别
#{}:SQL参数占位符
作用:#{}
用于将传入的参数安全地绑定到SQL语句中,它会自动使用PreparedStatement
的?
占位符机制,并且MyBatis会对传入的参数进行预处理(例如防止SQL注入)。
参数替换:在生成SQL语句时,#{}
会被替换为一个?
,然后由JDBC驱动程序将参数值绑定到这个?
占位符上。
使用场景:通常用于传递用户输入的参数,如查询条件、插入或更新的数据等。
示例:
<select id="findUserById" resultType="User"> SELECT * FROM users WHERE id = #{id} </select>
如果传入的
id
为1,MyBatis生成的SQL类似于:SELECT * FROM users WHERE id = ?
,然后通过PreparedStatement
将?
替换为1。
${}:SQL文本占位符
作用:${}
用于直接将传入的参数值替换到SQL语句中,它不会进行预处理,因此直接将参数值插入到SQL语句中。这意味着${}
会将参数视为SQL的一部分,可能会导致SQL注入风险。
参数替换:在生成SQL语句时,${}
会直接将传入的值替换到SQL语句中,而不会使用?
占位符。
使用场景:通常用于动态生成SQL片段,比如排序字段名、表名、列名等不直接来自用户输入的参数。
示例:
<select id="findUserByColumn" resultType="User"> SELECT * FROM users WHERE ${columnName} = #{value} </select>
如果传入的
columnName
为username
,value
为John
,MyBatis生成的SQL类似于:SELECT * FROM users WHERE username = ?
,然后通过PreparedStatement
将?
替换为John
。
2. 安全性和使用建议
SQL注入防护:由于
#{}
会使用PreparedStatement
的参数绑定机制,因此可以有效防止SQL注入攻击。而${}
直接将参数值拼接到SQL中,可能导致SQL注入,因此应慎重使用。动态SQL生成:
${}
更适合用于生成动态的SQL片段,比如动态表名、列名等。但要确保传入的值是可信任的,或者通过其他手段确保安全。
3. 具体示例
使用 #{} 的示例
<select id="findUserById" resultType="User"> SELECT * FROM users WHERE id = #{id} </select>
传入id
为1,生成SQL为:
SELECT * FROM users WHERE id = ?
然后将参数1安全地绑定到?
上。
使用 ${} 的示例
<select id="findUserByColumn" resultType="User"> SELECT * FROM users WHERE ${columnName} = #{value} </select>
传入columnName
为username
,value
为John
,生成SQL为:
SELECT * FROM users WHERE username = ?
然后将参数John
绑定到?
上。
SQL注入风险示例
<select id="findUserByColumn" resultType="User"> SELECT * FROM users WHERE ${columnName} = #{value} </select>
如果传入的columnName
为username OR '1'='1'
,生成的SQL可能是:
SELECT * FROM users WHERE username OR '1'='1' = ?
这样就可能导致SQL注入问题。
总结
#{}
:安全地传递参数,防止SQL注入,常用于传递用户输入的参数。${}
:直接将参数值插入到SQL中,适用于动态生成SQL片段(如表名、列名),但存在SQL注入风险,应谨慎使用。
在实际开发中,建议尽量使用#{}
来传递参数,以确保SQL安全性,而对于使用${}
的场景,需要确保传入的参数是安全且经过验证的。
到此这篇关于MyBatis中 /#{} 和 /${} 的区别小结的文章就介绍到这了,更多相关MyBatis /#{} 和 /${}内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!
最新评论