Arel,Joins和Rails查询

Jas*_*son 15 join arel ruby-on-rails-3

我最近在一段时间内遇到了一个问题,并找到了我去Arel的路,看起来它应该允许我在我的查询中做OR.

作为一个起点,我需要将现有的Rails 3查询转换为Arel,这就是我遇到问题的地方.

以下范围和查询按我的预期工作.它向我提供了与特定用户广告相关的请求.

#in the Request class
scope :responder, lambda { |user| joins(:ad).where(:ads => { :user_id => user }) }

Request.responder(303).to_sql

=> "SELECT \"requests\".* FROM \"requests\" INNER JOIN \"ads\" ON \"ads\".\"id\" = \"requests\".\"ad_id\" WHERE (\"ads\".\"user_id\" = 303)"
Run Code Online (Sandbox Code Playgroud)

根据Arel github页面和Railscast 215上的doco,我应该可以执行以下操作来使用Arel复制查询

  requests = Request.arel_table
  ads = Ad.arel_table
  where(requests.join(ads).on(ads[:id].eq(requests[:ad_id])))
Run Code Online (Sandbox Code Playgroud)

这会导致错误

TypeError: Cannot visit Arel::SelectManager
Run Code Online (Sandbox Code Playgroud)

我可以在控制台中执行以下操作

r = Request.arel_table
a = Ad.arel_table

r.join(a).to_sql
 => "SELECT  FROM \"requests\" INNER JOIN \"ads\" "
Run Code Online (Sandbox Code Playgroud)

所以看起来它正在形成SQL请求,但是当你把它放在哪里时

Request.where(r.join(a)).to_sql
Run Code Online (Sandbox Code Playgroud)

我得到以下内容

TypeError: Cannot visit Arel::SelectManager....
Run Code Online (Sandbox Code Playgroud)

我已经尝试在其中进行其他Arel动作并且它有效(例如)

Request.where(r[:status].eq(nil)).to_sql
 => "SELECT \"requests\".* FROM \"requests\" WHERE (\"requests\".\"status\" IS NULL)"
Run Code Online (Sandbox Code Playgroud)

这有点超出了我不断增长的rails/ruby​​知识.有任何想法吗?

提前致谢.

小智 9

你可以使用join_sources.firston Arel::SelectManager和pass这个加入

requests = Request.arel_table
ads = Ad.arel_table
Request.joins(requests.join(ads).on(ads[:id].eq(requests[:ad_id])).join_sources.first)
Run Code Online (Sandbox Code Playgroud)


nes*_*sur 8

这里更大的答案是,尽管这里有一些花哨,鼓舞人心的例子:http: //magicscalingsprinkles.wordpress.com/2010/01/28/why-i-wrote-arel/

... Active Record实际上并不支持完整的Arel功能.至少,不是通过关系或范围.您可以在Arel中创建任何(大多数)查询,但最终您将使用:

sql = User.arel_table.(something awesome in Arel).to_sql
users = User.find_by_sql(sql)
Run Code Online (Sandbox Code Playgroud)

从技术上讲,仍然有一个".to_a"方法,但它不会返回ActiveRecord模型实例,并且它已被弃用.

{} UPDATE

http://erniemiller.org/projects/squeel/是ActiveRecord发生的最好的事情.所有Arel的东西,实现了.

  • 你的wordpress链接已经死了 (2认同)

DGM*_*DGM 1

要在 Rails 3 中进行 OR 运算,请查看 MetaWhere。上面有一个很好的railscast:http://railscasts.com/episodes/251-metawhere-metasearch