class Module

Extension methods for {Module}

Definitions

Extension methods for {Module}

Public Instance Methods

canonical_rel_path() click to toggle source

Get the “canonical” lib-relative path for this module based off it's {#name} (via {String#underscore}, with `'.rb'` suffixed).

@todo

I bet ActiveSupport has some method for this re auto-loading.

@return [nil]

If this module is {#anonymous?}.

@return [Pathname]

If this module is not {#anonymous?}.
# File lib/nrser/core_ext/module/source_locations.rb, line 159
def canonical_rel_path
  if anonymous?
    nil
  else
    Pathname.new( name.underscore + '.rb' )
  end
end
class_Methods(include_super = true, sort: true)
class_method_locations(include_super = true, sort: true, only_valid: false) click to toggle source

Map class method names to the their source locations.

@see NRSER::Meta::Source::Location.for_methods

@param include_super (see Module#class_method_objects) @param sort: (see Module#class_method_objects) @param only_valid: (see NRSER::Meta::Source::Location.for_methods)

@return (see NRSER::Meta::Source::Location.for_methods)

# File lib/nrser/core_ext/module/source_locations.rb, line 46
def class_method_locations  include_super = true,
                            sort: true,
                            only_valid: false
  NRSER::Meta::Source::Location.for_methods \
    class_method_objects( include_super, sort: sort ),
    only_valid: only_valid
end
class_method_objects(include_super = true, sort: true) click to toggle source

Get class methods for this {Module} ({Class} are also {Module}, so works same for those).

@param include_super (see NRSER.method_objects_for) @param sort: (see NRSER.method_objects_for)

@return [Array<Method>]

List of method objects (all bound to `self`).
# File lib/nrser/core_ext/module/method_objects.rb, line 17
def class_method_objects include_super = true, sort: true
  NRSER.method_objects_for  self,
                            include_super,
                            type: :class,
                            sort: sort
end
Also aliased as: class_Methods
demod_name()

Because I always screw up spelling 'demodulize'

Alias for: demodulize_name
demodulize_name() click to toggle source

Get the {#safe_name} and run ActiveSupport's {String#demodulize} on it to get the module (or class) name without the namespace.

@example

NRSER::Types.demod_name
# => 'Types'

@return [String]

# File lib/nrser/core_ext/module/names.rb, line 61
def demodulize_name
  safe_name.demodulize
end
Also aliased as: demod_name
instance_Methods(include_super = true, sort: true, include_initialize: false)
instance_method_locations(include_super = true, sort: true, include_initialize: false, only_valid: false) click to toggle source

Map instance method names to the their source locations.

@see NRSER::Meta::Source::Location.for_methods

@param include_super (see Module#instance_method_objects) @param sort: (see Module#instance_method_objects) @param include_initialize: (see Module#instance_method_objects) @param only_valid: (see NRSER::Meta::Source::Location.for_methods)

@return (see NRSER::Meta::Source::Location.for_methods)

# File lib/nrser/core_ext/module/source_locations.rb, line 79
def instance_method_locations   include_super = true,
                                sort: true,
                                include_initialize: false,
                                only_valid: false
  NRSER::Meta::Source::Location.for_methods \
    instance_method_objects(
      include_super,
      sort: sort,
      include_initialize: include_initialize,
    ),
    only_valid: only_valid
end
instance_method_objects(include_super = true, sort: true, include_initialize: false) click to toggle source

Get instance methods for this {Module} (or {Class}).

@param include_super (see NRSER.method_objects_for) @param sort: (see NRSER.method_objects_for)

@param [Boolean] include_initialize

When `true`, include `#initialize` method if it's defined, which is
normally excluded from {Module#instance_methods}.

Respects  `include_super` - won't include it if we are only looking for
own instance methods and it's inherited.

@return [Array<UnboundMethod>]

List of method objects (all unbound).
# File lib/nrser/core_ext/module/method_objects.rb, line 59
def instance_method_objects include_super = true,
                            sort: true,
                            include_initialize: false
  NRSER.method_objects_for \
    self,
    include_super,
    type: :instance,
    sort: sort,
    include_initialize: include_initialize
end
Also aliased as: instance_Methods
method_locations(only_valid: false) click to toggle source

Get all source locations for that module (or class) methods - class and instance methods.

@param [Boolean] only_valid

Filter results to only valid source locations.

@return [Hash<Method, Array<String, Fixnum>>]

# File lib/nrser/core_ext/module/source_locations.rb, line 119
def method_locations only_valid: false
  # Get all the src locs for own methods
  # own_class_method_locations( only_valid: only_valid ).
  #   map { |name, location|
  #     [".#{ name }", location]
  #   }.
  #   to_h.
  #   merge! \
  #     own_instance_method_locations(  only_valid: only_valid,
  #                                     include_initialize: true ).
  #       map { |name, location|
  #         ["##{ name }", location]
  #       }.to_h
  
  [
    [ '.', own_class_method_locations(    only_valid: only_valid ) ],

    [ '#', own_instance_method_locations( only_valid: only_valid,
                                          include_initialize: true ) ],
    
  ].each_with_object( {} ) do |(prefix, method_locations), result|
    method_locations.each do |name, location|
      result["#{ prefix }#{ name }"] = location
    end
  end
end
own_class_Methods(sort: true)
own_class_method_locations(sort: true, only_valid: false) click to toggle source

Just calls {#class_method_locations} with `include_super = false`.

@param sort: (see class_method_locations) @param only_valid: (see class_method_locations)

@return (see class_method_locations)

# File lib/nrser/core_ext/module/source_locations.rb, line 62
def own_class_method_locations  sort: true,
                                only_valid: false
  class_method_locations false, sort: sort, only_valid: only_valid
end
own_class_method_objects(sort: true) click to toggle source

Just get the class methods defined in this module (or class) itself, omitting inherited ones.

Equivalent to

#class_method_objects false

@param sort: (see .class_method_objects) @return (see .class_method_objects)

# File lib/nrser/core_ext/module/method_objects.rb, line 37
def own_class_method_objects sort: true
  class_method_objects false, sort: sort
end
Also aliased as: own_class_Methods
own_instance_Methods(sort: true, include_initialize: false)
own_instance_method_locations(sort: true, include_initialize: false, only_valid: false) click to toggle source

Just calls {#instance_method_locations} with `include_super = false`.

@param sort: (see instance_method_locations) @param include_initialize: (see instance_method_locations) @param only_valid: (see NRSER::Meta::Source::Location.for_methods)

@return (see instance_method_locations)

# File lib/nrser/core_ext/module/source_locations.rb, line 101
def own_instance_method_locations sort: true,
                                  include_initialize: false,
                                  only_valid: false
  instance_method_locations false,
                            sort: sort,
                            include_initialize: include_initialize,
                            only_valid: only_valid
end
own_instance_method_objects(sort: true, include_initialize: false) click to toggle source

Just get the instance methods defined in this {Module} (or {Class}) itself, omitting inherited ones.

Equivalent to

#instance_method_objects false

@param sort: (see instance_method_objects) @param include_initialize: (see instance_method_objects)

@return (see instance_method_objects)

# File lib/nrser/core_ext/module/method_objects.rb, line 85
def own_instance_method_objects sort: true,
                                include_initialize: false
  instance_method_objects false,
                          sort: sort,
                          include_initialize: include_initialize
end
Also aliased as: own_instance_Methods
safe_name() click to toggle source

Like {Module#name} but also returns a {String} for anonymous classes.

So you don't need to do any testing or trying when you want to work with the name of a module (or class, which are modules).

@return [String]

# File lib/nrser/core_ext/module/names.rb, line 33
def safe_name
  name = self.name
  return name if name.is_a? String
  
  # Slice out whatever that hex thingy that anon modules dump in their
  # `#to_s`... `"#<Class:0x00007fa6958c1700>" => "0x00007fa6958c1700"`
  #
  # Might as well use that as an identifier so it matches their `#to_s`,
  # and this should still succeed in whatever funky way even if `#to_s`
  # returns something totally unexpected.
  #
  to_s_hex = self.to_s.split( ':' ).last[0...-1]
  
  type_name = if self.is_a?( Class ) then "Class" else "Module" end
  
  "Anon#{ type_name }_#{ to_s_hex }"
end
source_location() click to toggle source

Try to find a reasonable file and line for the module (or class) by looking at the locations of it's methods.

@return [NRSER::Meta::Source::Location]

Two entry array; first entry is the string file path, second is the
line number.

Note that both will be `nil` if we can't find a source location
(the location will not be {NRSER::Meta::Source::Location#valid?}).
# File lib/nrser/core_ext/module/source_locations.rb, line 178
def source_location
  # Get all the src locs for all methods
  locations = method_locations only_valid: true
  
  # Short circuit if we don't have shit to work with...
  return NRSER::Meta::Source::Location.new if locations.empty?
  
  # If any files end with the "canonical path" then use that. It's a path
  # suffix
  #
  #     "my_mod/sub_mod/some_class.rb"
  #
  # the for a class
  #
  #     MyMod::SubMod::SomeClass
  #
  canonical_rel_path = self.canonical_rel_path
  
  unless canonical_rel_path.nil?
    
    # Find first line in canonical path (if any)
    canonical_path_location = locations.
      values.
      find_all { |(path, line)| path.end_with? canonical_rel_path.to_s }.
      min_by { |(path, line)| line }
    
    # If we found one, we're done!
    return canonical_path_location if canonical_path_location
    
  end
  
  # OK, that didn't work, so...
  
  # If it's a {Class} and it has an `#initialize` method, point there.
  #
  if is_a?( Class ) && locations['#initialize']
    return locations['#initialize']
  end
  
  # No dice. Moving on...
  
  # Get the first line on the shortest path
  locations.values.min_by { |(path, line)|
    [path.length, line]
  }
end