Mybatis 中$和#千万不要乱用!
开头
这是一次代码优化过程中发现的问题,在功能优化后发现部分数据查不到出来了,问题就在于一条sql上的#和$。
下图为两条sql:
从图上可以看出 wwlr.LabelId in(${showLabels}) 和 wwlr.LabelId in(#{showLabels}),其中showLabels是传进来一个字符串类型的参数,参数的样子是这样的“4,44,514”,问题就出在这个参数传进来后#和$处理的方式是不一样的。
区别
1、#{ }是预编译处理,MyBatis在处理#{ }时,它会将sql中的#{ }替换为?,然后调用PreparedStatement的set方法来赋值,传入字符串后,会在值两边加上单引号,如上面的值 “4,44,514”就会变成“ '4,44,514' ”;
2、{ }是字符串替换, MyBatis在处理{ }时,它会将sql中的
注意:使用${ }会导致sql注入,不利于系统的安全性!
SQL注入:就是通过把SQL命令插入到Web表单提交或输入域名或页面请求的查询字符串,最终达到欺骗服务器执行恶意的SQL命令。常见的有匿名登录(在登录框输入恶意的字符串)、借助异常获取数据库信息等
应用场合:
1、#{ }:主要用户获取DAO中的参数数据,在映射文件的SQL语句中出现#{}表达式,底层会创建预编译的SQL;
2、{ }:主要用于获取配置文件数据,DAO接口中的参数信息,当出现在映射文件的SQL语句中时创建的不是预编译的SQL,而是字符串的拼接,有可能会导致SQL注入问题.所以一般使用
注:
${}获取DAO参数数据时,参数必须使用@param注解进行修饰或者使用下标或者参数#{param1}形式;
#{}获取DAO参数数据时,假如参数个数多于一个可有选择的使用@param。
问题分析
其实刚开始我也没太去看sql里的#和$,我把sql放到数据库跑一切正常,所以我就将代码的执行sql输出到控制台了,具体是这么一个输出sql的配置文件:
输出后,终于发现了问题在哪里。。。。
看了上面的区别介绍,相信大家其实都应该知道区别在哪里,我们的问题在哪里,其实就是sql在in的时候 ,里面的数据被加了两个双引号。“wwlr.LabelId in(4,44,514)就会变成 wwlr.LabelId in('4,44,514' );所以导致部分数据查不到了。
相关文章
- C生万物 | 深度挖掘数据在计算机内部的存储
- 一条sql执行很慢可能的原因,如何优化
- 【java】 java开发中 常遇到的各种难点 思路方案
- 写给大一同学的C语言--顺序结构
- 2023腾讯面试真题:
- 自学大数据第六天~HDFS命令(一)
- 大小端高位低位字节的理解
- echarts有滑块
- 数据仓库相关概念的解释
- MySQL性能优化
- Python-ABAQUS二次开发——切换ABAQUS自动生成rpy文件中的索引类型
- 【ArcGIS遇上Python】ArcGIS Python按照指定字段批量筛选不同类型的图斑(以土地利用数据为例)
- MySQL锁的分类和加锁机制
- Oracle调优日记
- ROS_DOMAIN_ID(ROS2域ID)
- 【水文模型】SWAT水文模型建立及应用(待更新)
- Java项目mysql查询只显示一行
- 2023年中职网络安全——SQL注入测试(PL)解析
- io流概述
- Windows下 int 和 long 数据类型为什么都占4个字节