I was reading another question with an answer that mentions using the Module#const_get instance method to find a class in a module. For example:
module M
class C
end
end
p M.const_get 'C'
#=> M::C
I was curious about the const_get method so I used ri and found:
ri Module#const_get
...
This method will recursively look up constant names if a namespaced
class name is provided. For example:
module Foo; class Bar; end end
Object.const_get 'Foo::Bar'
...
It seems like Object::const_get is a singleton method. Using it in our context works:
module M
class C
end
end
p Object.const_get 'M::C'
#=> M::C
But there's nothing documented about that singleton method:
ri Object::const_get
Nothing known about Object::const_get
ri Object.const_get
Nothing known about Object.const_get
This confused me because I know a Module is an Object but an Object is not a Module:
Module.ancestors
#=> [Module, Object, Kernel, BasicObject]
Object.ancestors
#=> [Object, Kernel, BasicObject]
Except then I used the Object#is_a? instance method to check and saw that I was wrong about that:
Module.is_a? Object
#=> true
Object.is_a? Module
#=> true
What started as an innocent ri query has led me to be confused about the entire Ruby object model.
Object.is_a? Module #=> true if Module is not in Objects ancestor chain?Object know about the const_get method?This is an artifact of the ill-understood separation between an object's class and an object's singleton class, a sort of shadow class that each class uses for things like this.
You can access this easily in Ruby 2.5+ with the singleton_class method:
Object.singleton_class.ancestors
# => [#<Class:Object>, #<Class:BasicObject>, Class, Module, Object, Kernel, BasicObject]
Where Module makes an appearance here, so that's how those methods get mixed in and are callable via Object.
Object itself has a comparatively dull inheritance chain:
Object.ancestors
#=> [Object, Kernel, BasicObject]
Every object in Ruby has a class, even Class is an Object, which also has an associated Class.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With