这一期,老王准备聊聊SQL注入攻击防御相关的内容。
SQL注入攻击和我们之前聊到过的XSS漏洞攻击很像,大体都是利用程序拼接字符串的原理来实现攻击效果。不同的是,一个是在前端web页面,而另一个则是针对后端数据库。那他到底是怎么样来攻击的呢,跟老王一起来吧~
1、实例
我们从一个实际的例子开始。加入我们要实现一个登录的功能,用户的帐号密码都放在数据库。这里为了简化,密码暂时认为是明文(实际使用中,一定要做加密或者摘要以后,再存入数据库,避免被人盗取)。
那么,当一个用户登录的时候,我们需要怎么做呢?我们的服务器会执行一条sql:
当用户输入用户名和密码的时候,就会执行上述sql语句,去判断是否存在。而且上面的sql初看是没什么问题的,对于用户正常的输入,他确实也没什么问题。
但是,如果用户不老实,输入了点不该输入的东西呢?
比如,name和password 都等于 " ' OR 1 = '1 ",我们代码执行以后,sql就变成了
大家仔细看看这句sql会有什么问题?他会将所有的用户都查出来,从而实现登录的目的。这样就可以轻易的获取我们系统的登录权限。如果这是一个银行系统……
我们再来看一个例子:
这个sql看起来也没什么问题,就是一个修改密码的语句。
但是,如果id为100的用户心狠手辣一点,输入了一个这样的新密码:"1';"。那我们上面这个sql就变成了:
那所有用户的密码就会被设置成1!他就可以尝试登录其他用户的帐号,而其他用户则不能登录。
以上两个例子是最为常见和普通的sql注入的例子。
2、防范
这些漏洞看起来都是很低级的,但是真正写代码的时候却非常容易忽略。那对于这类sql注入怎么来防范呢?
其实手段也是比较简单的,这个漏洞的根源在于拼SQL。所以,只要我们不拼SQL,或者是拼SQL不出错,就可以防范。因此,从这两个点出发,我们就有两种不同的思路:
a、不拼SQL
编程语言或者各数据库的API的里面几乎都有避免拼SQL的调用方式。比如,JAVA里面有一个叫做PreparedStatement的类,他接受参数化的sql:
这样,无论用户输入什么,都会以参数的形式来执行,而不会担心被截断注入。
b、避免拼接出错
为了防止用户乱输入,我们只需要将用户的输入进行转义,比如:"'" -> "\'"。这样,用户的输入就不会对sql造成影响。比如php中经常会用到的mysql_real_escape_string()这个函数,就可以将用户的输入进行标准化转义,从而避免SQL注入的攻击。
好了,以上两种防范措施都能比较好的解决sql注入的问题。不过,最重要的一点,就是我们在写程序的时候,一定要带着防御式编程的思想来考虑和看待问题:一切输入都是不靠谱的。所以在你的函数输入参数的判断上,严格!再严格!
俗话说病从口入,只要从源头上控制了,其实很多问题就都避免了。
老王今天的内容就聊到这里了!
不知道csdn官网有没有做?