mybatis中#{}与${}区别

mybatis 中使用 sqlMap 进行 sql 查询时,经常需要动态传递参数,例如sql 如下:

mybatis中#{}与${}区别

select * from student where uid=#{uid} AND student_name='${studentName}'

在动态 SQL 解析阶段, #{ } 和 ${ } 会有不同的表现:

#{ } 解析为一个 JDBC 预编译语句(prepared statement)的参数标记符占位符 ?。

上面的例子就被解析为

...... uid=?

${ } 仅仅为一个纯碎的 string 替换,在mybatis的动态 SQL 解析阶段将会进行变量替换。比如:传入的studentName参数是“张三”

...... student_name='张三'

最后解析完成的完整语句就是

select * from student where uid= ? AND student_name='张三'

然后把解析好的语句在通过JDBC执行。

所以因为在${ } 在预编译之前已经被变量替换了,这会存在 sql 注入问题。比如:传入的studentName参数是“1' OR '1'='1”

在mybatis中解析完成后变成了

select * from student where uid= ? AND student_name='1' OR '1'='1'

这样就查询出所有的数据了。

源码查看:

在执行mybtis的查询是,会执行到PreparedStatementHandler#query,查看生成的PreparedStatement

如果传入参数传入的studentName参数是“1' OR '1'='1”

所以就出现注入的情况了。

如果我们把${studentName}换成#{studentName},在传入“1' OR '1'='1”呢

在mybatis解析出的结果

在数据库的执行日志中查询执行的sql语句

发现我们传入的“'”被转义了,

所以通过预编译,用占位符的方式传值可以把一些特殊的字符进行转义,这样可以防止一些sql注入。

其原因就是:采用了JDBC的PreparedStatement,就会将sql语句:“select * from student where uid= ? AND student_name= ?” 预先编译好,也就是SQL引擎会预先进行语法分析,产生语法树,生成执行计划,也就是说,后面你输入的参数,无论你输入的是什么,都不会影响该SQL语句的语法结构了,因为语法分析已经完成了,而语法分析主要是分析sql命令,比如select,from,where,and,or,order by等等。所以即使你后面输入了这些sql命令,也不会被当成sql命令来执行了,因为这些SQL命令的执行,必须先得通过语法分析,生成执行计划,既然语法分析已经完成,已经预编译过了,那么后面输入的参数,是绝对不可能作为SQL命令来执行的,只会被当做字符串字面值参数。所以的sql语句预编译可以防御SQL注入。而且在多次执行同一个SQL时,能够提高效率。原因是SQL已编译好,再次执行时无需再编译。

默认使用PreparedStatement是不能执行预编译的,这需要在url中给出useServerPrepStmts=true参数(MySQL Server 4.1之前的版本是不支持预编译的,而Connector/J在5.0.5以后的版本,默认是没有开启预编译功能的)。

例如:jdbc:mysql://localhost:3306/test?useServerPrepStmts=true

这样才能保证mysql驱动会先把SQL语句发送给服务器进行预编译,然后在执行executeQuery()时只是把参数发送给服务器。

版权声明

1 本文地址:https://www.sunlonger.com/jijin/1230234.html 转载请注明出处。
2 本站内容除隼龙儿财经签约编辑原创以外,部分来源网络由互联网用户自发投稿及AIGC生成仅供学习参考。
3 文章观点仅代表原作者本人不代表本站立场,并不完全代表本站赞同其观点和对其真实性负责。
4 文章版权归原作者所有,部分转载文章仅为传播更多信息服务用户,如信息标记有误请联系管理员。
5 本站禁止以任何方式发布转载违法违规相关信息,如发现本站有涉嫌侵权/违规及任何不妥内容,请第一时间联系我们申诉反馈,经核实立即修正或删除。


本站仅提供信息存储空间服务,部分内容不拥有所有权,不承担相关法律责任。
上一篇 2024年06月17日
下一篇 2024年06月17日

相关推荐

  • 新手选好基金的关键与投资技巧 |基金宝典

    对于新手来说,选择基金是一个需要谨慎考虑的过程,首先,要明确自己的投资目标,是追求短期收益还是长期增值,或者是为了特定的财务目标(如子女教育、退休养老等)。同时,评估自己对投资风险的承受能力,风险承受能力较低的投资者可以选择低风险的货币市场基金或债券型基金

    2024-09-14 21:32:10
    0 0
  • 基金基础篇:一文讲透指数基金,干货满满

    投资千万条,风险第一条。前言:对于基金投资而言,绕不开的一个话题就是指数基金,那么到底什么是指数基金呢?它有哪些魅力呢?指数基金的优缺点是啥呢?等一系列问题,本篇就来展开详解,一起往下!对于基金老手而言,可以选择性阅读!01一、什么是指数?在说指数基金之前,

    2024-09-14 21:32:07
    0 0
  • 基金在什么平台上买比较合理?

    购买基金的平台,各有特点和优势,你可以根据自己的需求进行选择,以下是一些基金购买平台:1. 基金公司官方网站或APP:- 优点:直接从基金公司购买,能获取最准确的产品信息和相关服务,有时还可能享受费率优惠,比如申购费折扣等;对自家基金产品的研究和理解更深入,能提供

    2024-09-14 21:32:02
    0 0
  • 购买货币基金有哪些技巧?

    来源:龙老解股以下是购买货币基金的一些技巧: **一、选择规模适中的基金** 一般来说,规模适中的货币基金在市场上的议价能力较强,同时也能在操作上保持灵活性。如果规模过小,可能在应对大额赎回时面临流动性风险,并且在与银行等机构谈判获取更高利率时处于劣势;而规模过

    2024-09-14 21:31:59
    0 0
  • 【理财狮talk秀】债市也波动?别急,先看看这五要素

    据wind数据显示,今年开年以来债券市场吸引了大量资金的关注,走出了非常亮眼的行情,不过也引发了市场和监管对于持续上涨背后潜在风险的担忧。自8月5日以来,债券市场出现了明显的波动,债券价格持续下跌。走势相对较稳的债券为什么出现了较大的波动呢?今天,就让我们来聊一

    2024-09-14 21:31:58
    0 0
  • 几种止损的方式

    XX股票跌了好多,需要止损吗?关于这个问题,相信炒股的朋友都遇到过。买入被套后,不少人会选择原地躺下,等待股价回归。但事实上,随着A股越来越成熟,国际化进程越来越快,以往很多老股民的这个解套“经验”可能不那么灵了。运气不好的,甚至可能被套到退市!众所周知,投

    2024-09-14 21:31:56
    0 0

发表回复

8206

评论列表(0条)

    暂无评论