Join GitHub today
GitHub is home to over 20 million developers working together to host and review code, manage projects, and build software together.
Make constantize look down the ancestor chain (excluding Object) #6165
Unfortunately, the ancestor chain is not looked up at all.
I ran into this when registering an observer (say "some_class/observer"), where
One solution is for me to write:
I hope you appreciate the irony :-)
I feel that there is no reason for
This comment has been minimized.
This comment has been minimized.Show comment Hide comment
Also as implemented it wouldn't detect constants in the ancestors chain that appear after
def constantize(camel_cased_word) #:nodoc: names = camel_cased_word.split('::') names.shift if names.empty? || names.first.empty? names.inject(Object) do |constant, name| constant = constant.ancestors.detect(constant) do |ancestor| ancestor.const_defined?(name) unless ancestor == Object end constant.const_get(name, false) end end
One possible performance optimisation would be to let ruby search the ancestor chain by passing
@pixeltrix Thanks for your comment! I pushed a newer, shinier and better version that I dedicate to you :-)
On performance: the patch has basically no impact in cases where the constant seeked is directly owned by class/module, which are the cases handled correctly currently. For cases that are currently not handled properly, then yes, there will be a small performance difference, but slower is better than buggy!
In case the constant does not exist at all (even at the Object level or lower), the newer version will raise immediately, instead of looking down the chain for nothing.
As for the after Object bit, you're absolutely right for the top level search, and there was actually another bug in
On the other hand, when not looking up from
So thanks to your comments, I've fixed the top level search and also improved the performance of my patch in cases (top level or when constant doesn't exist at all).