1.SQL注入简介
SQL注入是普通常见的网络攻击方式之一,它的原理是通过在参数中输入特殊符号,来篡改并通过程序SQL语句的条件判断。
2.SQL注入攻击的思路
1.判断应用程序是否存在注入漏洞
判断方法:在参数后添加单引号" ' ",查看结果,譬如在登录时,用户名填为:1' 。或是url链接中:http://localhost/course/member/detail?id=1' 。
若是页面提示报错或是提示数据库错误的话,即说明存在SQL注入漏洞。
2.收集提示的数据库报错信息、判断数据库类型、猜解SQL语句、猜解表名、字段名,然后根据SQL注入漏洞与数据表名、字段名等对数据库进行攻击。
具体如何猜解,简而言之就是:根据数据库报错信息得出结果,原理很简单,但是工作量极大,没有经验的话,做起来很难。话说回来,如果SQL注入攻击那么容易的话,数据库就不用搞了。
这里我只简单的阐述SQL注入的原理与简单解决方法,再深入的我就不一一赘述了,有兴趣的大家可以自己谷歌。
3.SQL注入攻击实例
3.1最常见的SQL注入攻击在用户登录这一功能上。
毫无疑问,所有的用户登录SQL语句都形如:SELECT * FROM user WHERE name = ' " + userName + " ' and password= ' "+ password +" ';
常见的利用SQL注入攻破用户登录,关键在于在参数 "name" 或是 "password" 中插入特殊符号,以篡改程序SQL的条件判断。
譬如我们这样输入:
用户名:1' OR '1'='1
密码:1
那么程序接收到参数后,SQL语句就变成了:SELECT * FROM user WHERE name = '1' OR '1'='1 ' and password= '1';
恒为真,即可骗过程序,在没有账号密码的情况下成功登录。
我们也可以这样输入:
用户名:1
密码:1' OR '1'='1
那么程序接收到参数后,SQL语句就变成了:SELECT * FROM user WHERE name = '1' and password= '1' OR '1'='1 ';
同样恒为真,也可成功登录。
若是恶意攻击数据库,可以随意删除数据库信息,甚至连数据库都可以给你删掉,对项目造成毁灭性的打击,譬如:
用户名:1'; DROP DATABASE root;--
密码:1
那么程序接收到参数后,SQL语句就变成了:SELECT * FROM user WHERE name = '1'; DROP DATABASE root;--and password= '1';
由于分号;是SQL语句结束的标志,它会导致"SELECT * FROM user WHERE name = '1';" 后面的语句成为一条新的SQL语句,而--是SQL语句的单行注释标志,它会注释掉"and password= '1';"这一段,使整个SQL语句变的合法。然后 "DROP DATABASE root;"这一句直接把整个root数据库都删掉了。
这是被SQL注入攻击最严重的后果。
3.2 此外,只要是输入参数的SQL语句,都有被SQL注入攻击的威胁
譬如用户注册、用户个人信息修改、用户评论等等,凡是输入参数的地方,都有可能被SQL注入攻击。
譬如用户信息修改时,必然要传递判断参数,此时的SQL判断语句大都形如: UPDATE TABLENAME SET ''='' WHERE ''='' 。例如:update user set avatar='1.jpg' where id='1' 。
而判断参数有时就在url链接中,形如:http://localhost/course/member/detail?id=1 。说明程序很大可能是根据id进行SQL判断,如果该程序确实是根据用户id进行SQL判断。那么直接对url中传递的参数 " id=1 " 进行篡改,改成譬如: " id=1'; DROP DATABASE root;-- " ,那好,数据库root又被删没了。
再举例而言,如果用户不把判断参数放到url中,那么一般情况,技术人员把判断参数放到了保存按钮上,或是藏在某个隐藏的输入框里,再有就是cookie中,以及页面某个不起眼的角落中。此时的判断参数一般是id、name、phone其中一个,技术人员会通过表单提交或是ajax,将隐藏的判断参数以post方法提交到后台。此时,只要查看网页源代码,一般都能在提交按钮、隐藏输入框等角落里找到这个隐藏参数。譬如:<input type="button" name="meizi" onclick="addMember()" value="保存"> 这显然是一个将判断参数隐藏到提交按钮上的以ajax进行post提交的案例,判断参数为" meizi "。此时,我们按个F12,在源代码中将" name="meizi" "修改为" name="meizi'; DROP DATABASE root;--",好吧,root又没了。
4.如何防止SQL注入攻击
文章开头,我便说了,SQL注入攻击的原理就是通过在参数中输入特殊符号,来篡改并通过程序SQL语句的条件判断。那么最简单的办法就是在禁止用户向参数中写入特殊符号,这就是为什么所有网站的用户名默认不能包含特殊字符的原因。只要在表单提交之前、或是ajax提交之前,对参数进行一下js正则判断,对含有特殊符号的参数报错,就不用再担心SQL注入攻击啦。
此外,开发项目推荐使用框架编程,框架一般都自带库,能检查参数是否带有特殊符号。
譬如Thinkphp框架默认转义特殊符号,在参数中输入单引号 ' 或是双引号 " ,都会被默认加上一个 \ 进行转义,SQL注入攻击也就失效了。
再譬如,JSP中的PreparedStatement接口对象,会对SQL语句进行预编译,而SQL注入攻击只对SQL语句的编译过程有破坏作用,JSP中使用PreparedStatement接口进行预编译后,传入的参数只作为字符串,不会再进行一次编译,SQL注入攻击也就失效了。