Reputation: 2801
Using pry
, it's very simple to find where a method is defined and see the source by edit-method
command. Yet there is no correspondence for class itself. When that class has no methods defined itself, it's hard to locate the source through pry
.
Classes are constants, so it's equivalent to ask where to find the source in which a particular Ruby constant is defined. Thank you very much.
Upvotes: 37
Views: 10507
Reputation: 27374
There is a better way to do this as of Ruby 2.7, which is Module.const_source_location
.
> Admin.const_source_location(:LIMIT)
#=> ["SOME_PATH/user.rb", 2]
References:
Bonus from @ulysse-bn:
To have a quick access to this method, you can add it to IRB config like this:
~/.irbrc
# displays path of constant
#
# Usage:
#
# _source_location(::ActiveRecord::Base)
#
def _source_location(const)
Object.const_source_location(const.name)
end
Upvotes: 23
Reputation: 11396
A hacky way for debugging purposes: start a console (for instance with binding.irb
) and redefine the constant. You'll get an error message with the previous definition path!
> Foo = ""
(irb):11: warning: already initialized constant Foo
/path/to/foo.rb:1: warning: previous definition of Foo was here
=> ""
Upvotes: 5
Reputation: 2518
In ruby, $"
holds all the file names that are loaded via Kernel.load
.
So you could try something like this:
constant = User
$".detect{|load_path|
load_path.include?(constant.to_s.underscore)
}
Note: The method underscore
is part of Rails/ActiveSupport
Upvotes: 20
Reputation: 15828
If the constant you're looking for has methods (is a class or module) you can use the Method class to find out where it is defined.
class Foo
def bar
end
def self.baz
end
end
Foo.instance_method(:bar).source_location
Foo.method(:baz).source_location
A bit of a hack and doesn't help with pure constants class Foo; BAHZ = 2; end
but it is better than nothing.
Upvotes: 4
Reputation: 29895
Use ack, sometimes if I reach the limits of Pry (and Ruby) i resort to using it. Great thing about it is you can invoke it from within Pry itself using its shell integration features, usually just typing .ack ClassName
does the trick, however it requires that the class is defined in a file under the current directory.
In the case that the class is not defined in the current directory, then you can always resort to look up one of its methods, take the source location from there, and then use Pry's cat command to display it (with syntax highlighting) or Pry's edit command to jump directly to its definition.
The case where a class does NOT have any instance methods defined is fairly rare -- and such a class is usually quite uninteresting anyway :)
EDIT:
The most recent version of Pry (0.9.9) can now show the source for modules/classes using the normal show-source
command. It requires that the module/class has at least one defined method however
Upvotes: 8
Reputation: 7111
Well you could try Module.constants(true)
as stated here It might take a bit more than using pry
offers but it would allow you a chance to peek into the Modules involved
Upvotes: 2