zoukankan      html  css  js  c++  java
  • web安全防范之SQL注入攻击、攻击原理和防范措施 --

    SQL注入

    攻击原理

    在编写SQL语句时,如果直接将用户传入的数据作为参数使用字符串拼接的方式插入到SQL查询中,那么攻击者可以通过注入其他语句来执行攻击操作,这些攻击包括可以通过SQL语句做的任何事:获取敏感数据、修改数据、删除数据库表等

    攻击示例

    假设我们的程序是一个学生信息查询程序,其中的某个视图函数接收用户输入的密码,返回根据密码查询对应的数据。我们的数据库有一个db对象表示,SQL语句通过execute()方法执行:

    @app.route('/students')
    def bobby_table():
        password = request.args.get('password')
        cur = db.execute("SELECT * FROM students WHERE password = '%s';" %password)#直接使用用户输入的数据执行sql
       
    results = cur.fetchall()
        return results

    在实际应用中,敏感数据需要通过表单提交的POST请求接收,这里为了便于演示,通过查询参数接收。

    我们通过查询字符串获取用户插入的查询参数,并且不经过任何处理就使用字符串格式化的方法拼接到SQL语句中。在这种情况下,如果攻击者输入的参数值为” ‘or 1 =1”,即http://example.com/students?password=’or 1=1 --,那么视图函数中被执行的SQL语句就变成:

    select * from students where password=’’ or 1=1 --;’

    这时会把students表中所有记录全部查询并返回,也就意味着所有的记录都被攻击者窃取了。更可怕的是,如果攻击者将password参数的值设为”’; drop table users; --”,那么查询语句就会变成:

    select * from students where password=’ ’; drop table users; --’

    这个语句会把students表中所有的记录全部删掉。

    在SQL中,“;”用来结束一行语句;“--”用来注视后边的语句,类似python的”#”。

    主要防范方法

    验证输入类型

    比如某个视图函数接收整形id来查询,那么就在URL规则中限制URL变量为整形。

    参数化查询

    在构造SQL语句时避免使用拼接字符串或字符串格式化(使用百分号或format()方法)的方式来构建SQL语句。而要使用各类接口库提供的参数化查询方法,以mysql为例:

    db.execute(‘select * from students where password=@password’),此时,即使password的值是“’ or 1=1 --”话,那么SQL在执行的时候会把password这个变量单独进行解析:

    @password=’’ or 1=1 –‘,并不会像拼接字符串那样使这个SQL执行其他的动作,所以就不会被注入了

    转义特使字符

    比如引号、分号和横线等。使用参数化查询时,各种接口库会为我们做转义工作。

  • 相关阅读:
    Spring Annotation注解进行aop的学习
    使用ADO读取SQL数据库
    GetInventTable组装SQL语句使用通配符
    获取当前用户所属的所有仓位,DictRelation,
    UnitConvert,单位换算,单位转换
    数字货币书写转英文货币书写
    导出xml
    存储过程IN参数疑难问题解决方法
    TempTable 临时表
    多栏报表 多列报表
  • 原文地址:https://www.cnblogs.com/xiaxiaoxu/p/10424766.html
Copyright © 2011-2022 走看看