esolve
V2EX  ›  问与答

Mybatis 里,说用$,会产生 sql 注入的问题,这个如何理解?

  •  
  •   esolve · Apr 4, 2017 · 2487 views
    This topic created in 3346 days ago, the information mentioned may be changed or developed.
    5 replies    2017-04-05 03:40:44 +08:00
    ixiaozhi
        1
    ixiaozhi  
       Apr 4, 2017
    select * from table where id = ${id} =====> ${id} -> 1;drop table ....... =====> select * from table where title = 1; drop table .....
    unifier
        2
    unifier  
       Apr 4, 2017
    @ixiaozhi 我猜 lz 是在问 $ 和 # 的区别
    ixiaohei
        3
    ixiaohei  
       Apr 4, 2017
    $是静态替换,相当于最后替换字符串。#是动态的,原理是 prepearStatement 占位符。应该是 JDBC 驱动做的转换,比较安全,推荐方式。但是很多场景 prepearStatement 处理不了,我记得替换表名应该是处理不了要用$,其他的用#。具体可以 mybatis 源代码,做了两步转换的。第一步静态替换就是处理$。第二部处理#.
    esolve
        4
    esolve  
    OP
       Apr 4, 2017
    @ixiaozhi 你意思是 譬如
    select * from table where username = ${name}

    用户在对话框输入一个用户名为 1;drop table
    然后就 select * from table where username = 1; drop table

    如果 select * from table where username = #{name}
    用户输入 1;drop table

    select * from table where username = “ 1; drop table ”

    这样#使得这个 sql 无效
    而$使得 sql 有效?
    msg7086
        5
    msg7086  
       Apr 5, 2017
    @esolve 我没用过 Mybatis ,只从通用的场景来回答。
    当你用占位符的时候,字符串是不会拼接进语句的。
    所以数据库处理的 SQL 语句仍然是
    SELECT * FROM table WHERE username = 占位符
    然后实际查询时,数据库会用占位符去请求的参数里找,找到 Params[0]的内容,直接拿去做内容比较。
    About   ·   Help   ·   Advertise   ·   Blog   ·   API   ·   FAQ   ·   Solana   ·   6009 Online   Highest 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 50ms · UTC 03:06 · PVG 11:06 · LAX 20:06 · JFK 23:06
    ♥ Do have faith in what you're doing.