这个python / mysql查询容易受到SQL注入攻击吗

时间:2019-11-05 21:14:59

标签: python mysql sql-injection

我目前正在查看某人的代码,并且遇到了以下Python行:

db.query('''SELECT foo FROM bar WHERE id = %r''' % id)

这违背了我的常识,因为我通常会选择使用准备好的语句,或者至少使用数据库系统的本机字符串转义功能。

但是,鉴于以下情况,我仍然很好奇如何加以利用:

  1. “ id”值是由最终用户/ pentester提供的字符串或数字。
  2. 这是MySQL
  3. 该连接已明确设置为使用UTF8。

1 个答案:

答案 0 :(得分:1)

MySQL的Python驱动程序不支持真正的预备语句。它们都执行某种形式的字符串插值。诀窍是让Python以适当的转义进行字符串插值。

观看不安全操作的演示:How do PyMySQL prevent user from sql injection attack?

模拟参数的常规方法如下:

{
  cards: 
    [
      {
        reference: "",
        response: {
                    text: "",
                    title: "",
                  },
        timestamp: ""
      },

      {
        reference: "",
        response: {
                    text: "",
                    title: "",
                  },
        timestamp: ""
      },

     .... and so on

请参见https://dev.mysql.com/doc/connector-python/en/connector-python-api-mysqlcursor-execute.html


我知道克服转义的唯一方法(正确完成时)是:

  • 利用GBK或S​​JIS或类似的字符集,其中转义的引号成为多字节字符的一部分。通过确保sql = "SELECT foo FROM bar WHERE id = %s" cursor.execute(sql, (id,)) ,您应该可以避免此问题。
  • 更改set names utf8以打破转义,例如启用sql_modeNO_BACKSLASH_ESCAPES。您应该在会话开始时设置ANSI_QUOTES,类似于设置名称的方式。这样可以确保它不会使用引起问题的全局更改的sql_mode。

另请参阅Is "mysqli_real_escape_string" enough to avoid SQL injection or other SQL attacks?

相关问题