【问题标题】:Rails Arel and Active Record predicatesRails Arel 和 Active Record 谓词
【发布时间】:2011-10-15 19:30:48
【问题描述】:

我可能对 Rails 中的 Arel 对象缺乏一些了解。

你可以这样做:

u = User.arel_table

然后和疯狂的查询添加,例如:

u.join(:microposts)

(隐式 .on(users[:user_id]) )。

但是如何将 Arel 关系转换为 Rails 对象列表?

更新

一个更好的例子是这个。我刚刚完成了 Michael Hartl 的 Rails 教程,他在 Micropost 控制器中做了类似的事情:

  followed_ids  = %(SELECT followed_id FROM relationships WHERE follower_id = :user_id)
  where("user_id in (#{followed_ids}) OR user_id = :user_id", :user_id => user)

我讨厌原始的 SQL。所以我想重构,到目前为止我最好的就是这样:

followed_ids  = Relationship.select(:followed_id).where(:follower_id => user) 
where("user_id in (#{followed_ids.to_sql}) OR user_id = :user_id", :user_id => user)

我曾经将 .map(&:followed_id).join(", ") 添加到关系选择中,它也可以工作,但是你在内存中拥有所有 id,而不是一个简短的选择语句供数据库处理。

我的问题是,当它拥有返回我的对象​​所需的一切时,我似乎需要做一个 .to_sql 来提供给 where 并让它快乐。我正在考虑切换到可以很好地执行子查询的 Squeel,但我想了解 Arel。

【问题讨论】:

    标签: sql ruby-on-rails activerecord arel


    【解决方案1】:

    你可以的

    User.joins(User.arel_table.joins(:microposts))
    

    但这没什么意义,因为您只需执行User.joins(:microposts) 并获得相同的结果。但是,如果您必须创建一些更复杂的连接,它可能会很方便。

    不过,这样的东西可能很有用。

    User.where(User.arel_table[:name].matches('John%'))
    

    请记住,虽然您可以利用 Rails 中的一些核心 Arel 东西,但通常最好坚持使用 .where(:name=>'John').where('name LIKE ?', 'John%') 等更简单的方法,因为 Rails 无论如何都会在幕后将它们变成 Arel 对象。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多