假设我在Rails 3应用程序的页面上有一个搜索框,您可以按业务名称或城市搜索客户端。在我的控制器的索引方法中,我这样做:
if params[:search]
@clients = Client.where("clients.business_name LIKE :business_name OR clients.city = :city", :business_name => "%#{params[:search]}%", :city => params[:search])
这些哈希值被替换为SQL并用引号括起来。如果我在搜索框中的输入包含引号或其他危险字符,我会在开发日志中看到它们被转义,例如:
... WHERE(clients.business_name LIKE'%Something \'DROP TABLE Foo%'...
或者
...WHERE... OR clients.city = 'Something OR 1=1')
因此,由于OR 1=1
在Rails添加的引号内,因此它不会产生城市名称的匹配,并且由于DROP TABLE
尝试中的引用被转义,因此它也不会产生匹配公司名称。
这不是使用实际准备好的语句,其中查询首先发送到数据库而没有填写搜索值,然后将搜索值发送到数据库以填写。我认为这是最安全的方法但是Rails没有这样做;我认为这是因为它并不适用于所有数据库和实现方式。
这是以某种方式对SQL注入开放吗?我没有看到它,但是再次,它没有使用预准备语句,所以我想知道。 如果存在漏洞,我该如何更安全地执行此操作?
答案 0 :(得分:5)
不,这里没有SQL注入漏洞。 ActiveRecord会将您传入的哈希值connection.quote
作为第二个参数调用where
,这样您就可以安全了。
我能想到的唯一可能的SQL注入点是connection.quote
中是否有一些未被发现的错误,这是不太可能的。