How to get the modules included in the class

How can I get an array of modules included in a class, except for those that slipped through inheritance?

Note that ancestors, <=>, included_moduleswill not work, because the results do not distinguish between the modules that are included in modules that are added to the superclass. In other words, they cannot distinguish between the following two cases:

  • M added to superclass B

    class A; end
    class B < A; end
    module M; end
    A.prepend M
    
    B.ancestors # => [B, M, A, Object, Kernel, BasicObject]
    B <=> M # => -1
    B.included_modules # => [M, Kernel]
    
  • M included in B

    class A; end
    class B < A; end
    module M; end
    B.include M
    
    B.ancestors # => [B, M, A, Object, Kernel, BasicObject]
    B <=> M # => -1
    B.included_modules # => [M, Kernel]
    
+4
source share
1 answer
mixed_in  = B.included_modules[0...-B.superclass.included_modules.size]
prepended = B.ancestors.take_while { |ancestor| ancestor != B }
included  = mixed_in - prepended
+2
source

Source: https://habr.com/ru/post/1621897/


All Articles