提交 22fa48f2 编写于 作者: R Ryuta Kamizono

Mixin `CollectionProxy::DelegateExtending` after `ClassSpecificRelation`

`ClassSpecificRelation` has `method_missing` and the `method_missing` is
called first. if an associated class has the missing method in a
relation, never reach to the `method_missing` in the `CollectionProxy`.
I extracted `DelegateExtending` and included it to the delegate class
that including `ClassSpecificRelation` to fix the issue.

Fixes https://github.com/rails/rails/pull/28246#issuecomment-296033784.
上级 0541a0d5
......@@ -1121,6 +1121,19 @@ def reset
delegate(*delegate_methods, to: :scope)
module DelegateExtending # :nodoc:
private
def method_missing(method, *args, &block)
extending_values = association_scope.extending_values
if extending_values.any? && (extending_values - self.class.included_modules).any?
self.class.include(*extending_values)
public_send(method, *args, &block)
else
super
end
end
end
private
def find_nth_with_limit(index, limit)
......@@ -1141,21 +1154,16 @@ def find_from_target?
@association.find_from_target?
end
def association_scope
@association.association_scope
end
def exec_queries
load_target
end
def respond_to_missing?(method, _)
scope.respond_to?(method) || super
end
def method_missing(method, *args, &block)
if scope.respond_to?(method) && scope.extending_values.any?
extend(*scope.extending_values)
public_send(method, *args, &block)
else
super
end
association_scope.respond_to?(method) || super
end
end
end
......
......@@ -25,6 +25,8 @@ def initialize_relation_delegate_cache
def inherited(child_class)
child_class.initialize_relation_delegate_cache
delegate = child_class.relation_delegate_class(ActiveRecord::Associations::CollectionProxy)
delegate.include ActiveRecord::Associations::CollectionProxy::DelegateExtending
super
end
end
......
......@@ -19,6 +19,11 @@ class Comment < ActiveRecord::Base
has_many :children, class_name: "Comment", foreign_key: :parent_id
belongs_to :parent, class_name: "Comment", counter_cache: :children_count
# Should not be called if extending modules that having the method exists on an association.
def self.greeting
raise
end
def self.what_are_you
"a comment..."
end
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册