我一直在查看 ActiveRecord 源以了解:if => proc_or_method_name
ActiveRecord 验证的工作原理,但源中唯一的实例:if
是在解释如何调用该功能的注释中。
例如,您可以在模型中有如下一行:
validates_presence_of :name, :if => :nameable?
nameable?
并且只有在方法返回给定模型的真实值时才会检查验证。
这个功能实际定义在哪里,因为我在(Rails2)源中的任何地方都找不到这种行为?
我一直在查看 ActiveRecord 源以了解:if => proc_or_method_name
ActiveRecord 验证的工作原理,但源中唯一的实例:if
是在解释如何调用该功能的注释中。
例如,您可以在模型中有如下一行:
validates_presence_of :name, :if => :nameable?
nameable?
并且只有在方法返回给定模型的真实值时才会检查验证。
这个功能实际定义在哪里,因为我在(Rails2)源中的任何地方都找不到这种行为?
从 Rails 3 开始,ActiveRecord 回调定义在active_record/callbacks.rb中,但是因为 ActiveRecord 模型继承自 ActiveModel,所以您还应该查看active_model/callbacks.rb文件。
回调功能本身是一个单独的组件。事实上,ActionController before/after 过滤器实际上是回调。出于这个原因,回调系统是一个定义在ActiveSupport::Callbacks中的模块。
将这 3 个部分完全合并,您将获得 ActiveRecord 回调功能。
在文件中检查了该:if
选项activesupport\lib\active_support\callbacks.rb
。
调用该方法should_run_callback
以检查是否应执行回调。
还要看看回调链是如何处理的,从run_callbacks
同一个文件中的方法开始。
该文件的 v2.3.8 中的一些代码是:
def should_run_callback?(*args)
[options[:if]].flatten.compact.all? { |a| evaluate_method(a, *args) } &&
![options[:unless]].flatten.compact.any? { |a| evaluate_method(a, *args) }
end
这是我发现的(以防有人感兴趣):
:if
在所有 .rb 文件中进行了 greppactiverecord/CHANGELOG
中,有一条评论提到:
:if
对工作原理有所了解:if
并检查每个感觉“好”的文件。来到activesupport/lib/active_support/callbacks.rb
:if
,它仅在方法中的一个位置找到should_run_callback
。那很有趣!