【发布时间】:2014-06-25 02:27:21
【问题描述】:
我正在学习 RoR/数据库,这个话题让我特别困惑。在 Agile Development with Rails 4 一书中,他们给出了一个示例,用于查找名称为 Dave 的条目的所有订单列表:
pos = Order.where("name = 'Dave' and pay_type = 'po")
这本书接着说,你永远不会想做这样的事情:
name = params[:name]
pos = Order.where("name = '#{name}'and pay_type = 'po'")
您应该这样做:
name = params[:name]
pos = Order.where(["name = ? and pay_type = 'po'",name])
我明白,SQL 注入是一个概念,但有一些细节让我感到困惑。对于初学者来说,SQL 注入作为一种语法究竟是如何工作的。
我知道危险在于,如果您像第一个示例那样插入外部表单参数,那么有人可能会删除表/数据库,但如何?
假设你有这个:
name = params[:name] #DROP DATABASE database_name
pos = Order.where("name = '#{DROP DATABASE database_name}'and pay_type = 'po'")
这就是 SQL 注入的工作原理吗? SQL是一种语法,数据库中应该没有“name = DROP DATABASE database_name”的字段,这不会返回错误而不是删除数据库吗?
另外,问号版本如何防止这种情况发生。同样,假设您有这种情况。
name = params[:name] #DROP DATABASE database_name
pos = Order.where(["name = ? and pay_type = 'po'", DROP DATABASE database_name])
这不会用 DROP DATABASE database_name 语法替换问号,那么我们会不会遇到与第一个示例中相同的问题?这究竟如何保护应用程序免受 SQL 攻击?我在http://hub.tutsplus.com/ 上搜索了一些教程并在谷歌上搜索,但我不明白它背后的概念。有什么帮助吗?
【问题讨论】:
-
这似乎相关:xkcd.com/327
-
感谢 Ellesedil 的快速回复,我以前确实见过这个,但我不明白它是如何工作的。正如我在上面的问题中提到的,问号会被变量名替换,就像第一个没有它的例子一样,所以基本上你会插入相同的删除表语法。还是谢谢
-
这并不完全是重复的,但大部分可以由the seminal PHP injection question回答。
标签: sql ruby-on-rails ruby sql-injection