2010-07-31 132 views
1

我爱新的铁路3!Rails 3:sql注入免费查询

新的查询语法是如此真棒:

users = User.where(:name => 'Bob', :last_name => 'Brown') 

但是,当我们需要做的是这样

SELECT * FROM Users WHERE Age >= const AND Money > const2 

我们必须使用

users = User.where('Age >= ? and money > ?', const, const2) 

这是不是很冷静。下面的查询是不是安全的,因为SQL注入:

users = User.where('Age >= #{const} and money > #{const2}') 

我喜欢的C#/ LINQ版本

var users = DB.Where(u => u.Age >= const && u.Money > const2); 

有没有办法做这样的事情,在Rails的?

回答

6

新的查询与轨道不容易受到SQL注入。参数中的任何引号都会被转义。

Rails 3 AR获得了LINQ已经有一段时间的延迟执行。这可以让您链接任何查询方法。你唯一一次有把2个或更多的零件放到哪里,当你想要一个OR

除此之外,有很多不同的方式来做你的查询。

Users.where('age >= ?', age).where('money > ?', money) 
Users.where('age >= ? and money > ?', age, money) 

class User < ActiveRecord::Base 
    scope :aged, lambda { |age| where('age >= ?', age) } 
    scope :enough_money, lambda { |money| where('money > ?', money) } 

    scope :can_admit, lambda { |age, money| aged(age).enough_money(money) } 
end 

Users.aged(18).enough_money(200) 
Users.can_admit(18, 200) 
+0

谢谢!这就是我一直在寻找的。 – Alex 2010-08-03 07:01:10

2

在Rails 3中,您可以将这些选择链接在一起。我不是上来就特定的语法,但是这是一个良好的开端:http://railscasts.com/episodes/202-active-record-queries-in-rails-3

的基本概念是,你可以链在一起作用域或where子句等:

元代码在这里:

users = User.where(:age_of_consent).where(:has_credit) 

scope :age_of_consent where("age >= ?", 18) 
scope :has_credit where("credit > ?", 10) 
3

您可能会感兴趣MetaWhere与您可以写:

users = User.where(:age >= const, :money > const2) 
1

可以传递命名参数的哈希来查询是对匿名位置参数的改进。

users = User.where('Age >= ? and money > ?', const, const2) 

变(是为更类似于LINQ语法)

users = User.where('Age >= :const and money > :const2', {:const => const, :const2 => const2})