提交 9698c1bf 编写于 作者: R Ryuta Kamizono

Fix `unscope` when an `eq` node which has no arel attribute

Current code expect an `eq` node has one arel attribute at least, but an
`eq` node may have no arel attribute (e.g. `Arel.sql("...").eq(...)`).

In that case `unscope` will raise `NoMethodError`:

```
% bundle exec ruby -w -Itest test/cases/relations_test.rb -n test_unscope_with_arel_sql
Using sqlite3
Run options: -n test_unscope_with_arel_sql --seed 4477

# Running:

E

Error:
RelationTest#test_unscope_with_arel_sql:
NoMethodError: undefined method `name' for #<Arel::Nodes::Quoted:0x00007f9938e55960>
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/active_record/relation/where_clause.rb:157:in `block (2 levels) in except_predicates'
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/arel.rb:57:in `fetch_attribute'
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/active_record/relation/where_clause.rb:157:in `block in except_predicates'
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/active_record/relation/where_clause.rb:156:in `reject'
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/active_record/relation/where_clause.rb:156:in `except_predicates'
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/active_record/relation/where_clause.rb:31:in `except'
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/active_record/relation/query_methods.rb:487:in `block (2 levels) in unscope!'
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/active_record/relation/query_methods.rb:481:in `each'
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/active_record/relation/query_methods.rb:481:in `block in unscope!'
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/active_record/relation/query_methods.rb:471:in `each'
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/active_record/relation/query_methods.rb:471:in `unscope!'
    /Users/kamipo/src/github.com/rails/rails/activerecord/lib/active_record/relation/query_methods.rb:464:in `unscope'
    test/cases/relations_test.rb:2062:in `test_unscope_with_arel_sql'
```

We should check for both `value.left` and `value.right` those are arel
attribute or not.
上级 79ba0694
......@@ -53,7 +53,7 @@ def self.fetch_attribute(value, &block) # :nodoc:
Arel::Nodes::GreaterThan, Arel::Nodes::GreaterThanOrEqual
if value.left.is_a?(Arel::Attributes::Attribute)
yield value.left
else
elsif value.right.is_a?(Arel::Attributes::Attribute)
yield value.right
end
when Arel::Nodes::Or
......
......@@ -2050,6 +2050,18 @@ def test_unscope_specific_where_value
assert_equal 1, posts.unscope(where: :body).count
end
def test_unscope_with_arel_sql
posts = Post.where(Arel.sql("'Welcome to the weblog'").eq(Post.arel_attribute(:title)))
assert_equal 1, posts.count
assert_equal Post.count, posts.unscope(where: :title).count
posts = Post.where(Arel.sql("posts.title").eq("Welcome to the weblog"))
assert_equal 1, posts.count
assert_equal 1, posts.unscope(where: :title).count
end
def test_unscope_grouped_where
posts = Post.where(
title: ["Welcome to the weblog", "So I was thinking", nil]
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册