mirror of
https://github.com/rails/rails.git
synced 2022-11-09 12:12:34 -05:00
Precompute Inheritance.base_class
This saves checking the inehritance chain on each access.
This commit is contained in:
parent
99049262d3
commit
7abd9b5f66
2 changed files with 25 additions and 13 deletions
|
@ -43,6 +43,8 @@ module ActiveRecord
|
|||
# Determines whether to store the full constant name including namespace when using STI.
|
||||
# This is true, by default.
|
||||
class_attribute :store_full_sti_class, instance_writer: false, default: true
|
||||
|
||||
set_base_class
|
||||
end
|
||||
|
||||
module ClassMethods
|
||||
|
@ -98,17 +100,7 @@ module ActiveRecord
|
|||
#
|
||||
# If B < A and C < B and if A is an abstract_class then both B.base_class
|
||||
# and C.base_class would return B as the answer since A is an abstract_class.
|
||||
def base_class
|
||||
unless self < Base
|
||||
raise ActiveRecordError, "#{name} doesn't belong in a hierarchy descending from ActiveRecord"
|
||||
end
|
||||
|
||||
if superclass == Base || superclass.abstract_class?
|
||||
self
|
||||
else
|
||||
superclass.base_class
|
||||
end
|
||||
end
|
||||
attr_reader :base_class
|
||||
|
||||
# Returns whether the class is a base class.
|
||||
# See #base_class for more information.
|
||||
|
@ -218,6 +210,7 @@ module ActiveRecord
|
|||
end
|
||||
|
||||
def inherited(subclass)
|
||||
subclass.set_base_class
|
||||
subclass.instance_variable_set(:@_type_candidates_cache, Concurrent::Map.new)
|
||||
super
|
||||
end
|
||||
|
@ -253,6 +246,24 @@ module ActiveRecord
|
|||
end
|
||||
end
|
||||
|
||||
def set_base_class # :nodoc:
|
||||
@base_class = begin
|
||||
if self == Base
|
||||
self
|
||||
else
|
||||
unless self < Base
|
||||
raise ActiveRecordError, "#{name} doesn't belong in a hierarchy descending from ActiveRecord"
|
||||
end
|
||||
|
||||
if superclass == Base || superclass.abstract_class?
|
||||
self
|
||||
else
|
||||
superclass.base_class
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
private
|
||||
# Called by +instantiate+ to decide which class to use for a new
|
||||
# record instance. For single-table inheritance, we check the record
|
||||
|
|
|
@ -190,8 +190,9 @@ class InheritanceTest < ActiveRecord::TestCase
|
|||
end
|
||||
|
||||
def test_base_class_activerecord_error
|
||||
klass = Class.new { include ActiveRecord::Inheritance }
|
||||
assert_raise(ActiveRecord::ActiveRecordError) { klass.base_class }
|
||||
assert_raise(ActiveRecord::ActiveRecordError) do
|
||||
Class.new { include ActiveRecord::Inheritance }
|
||||
end
|
||||
end
|
||||
|
||||
def test_a_bad_type_column
|
||||
|
|
Loading…
Reference in a new issue