SQL注入

SQL注入,通过把SQL命令插入到Web表单或输入域名或页面请求的查询字符串,最终达到欺骗服务器执行恶意的SQL命令。

SQL是一种用于管理数据库的查询语言。使用它可以增删改查存储在数据库中的数据,在某些情况下你甚至可以使用SQL命令去执行一些操作系统命令,因此一个成功的SQL注入可以引起非常严重的后果。

SQL注入可能造成的一些后果:

  • 攻击者可以使用SQL注入得到其他用户的数据库凭证,然后他们能模仿这些数据库用户。
  • 攻击者可以使用SQL注入从数据库中选择并输出数据
  • 攻击者可以是使用SQL注入改变、增加、删除数据,甚至删除数据表。
  • 在一些数据库中,你可以使用数据库系统访问操作系统。

SQL注入的一些例子:

1. 拼接SQL:
# Define POST variables
uname = request.POST['username']
passwd = request.POST['password']

# SQL query vulnerable to SQLi
sql = “SELECT id FROM users WHERE username=’” + uname + “’ AND password=’” + passwd + “’”

# Execute the SQL statement
database.execute(sql)

用户可以传入一个单引号,设置password字段值为:

password' OR 1=1

用户也可以添加注释使SQL 语句忽略掉后面的查询条件

2. 基于union的SQL注入
GET http://testphp.vulnweb.com/artists.php?artist=1 HTTP/1.1
Host: testphp.vulnweb.com

GET http://testphp.vulnweb.com/artists.php?artist=-1 UNION SELECT 1,pass,cc FROM users WHERE uname='test' HTTP/1.1
Host: testphp.vulnweb.com

SQL 注入预防

对于后端程序员,我感觉不使用动态拼接SQL,使用参数化SQL就可以达到了。一些ORM也是采用的此种方式,比如Django。如果有能在参数化SQL中实现SQL注入的方式请告知,非常感谢

参数化SQL:

在使用参数化查询的情况下,数据库服务器不会将参数的内容视为SQL指令的一部份来处理,而是在数据库完成 SQL指令的编译后,才套用参数运行,因此就算参数中含有恶意的指令,由于已经编译完成,就不会被数据库所运行。

一些其他的防护

  • 永远不要使用管理员权限的数据库连接,为每个应用使用单独的权限有限的数据库连接。(我感觉一般是DBA的工作,他们给啥类型的用户我们也就只能用啥)
  • 不要把机密信息直接存放,加密或者hash掉密码和敏感的信息。(主要防止数据库被连接或注入成功后得到该类信息)
  • 给用户展示的应用的异常信息,不应该是数据库的返回,或者程序的异常信息,应该根据异常类别给出提示信息。(暴露越少的应用信息对于程序越安全,对用户的体验也越少,他们可能不懂)

你可能感兴趣的:(SQL注入)