Class: Pry::Method

Inherits:
Object show all
Extended by:
Helpers::BaseHelpers
Includes:
CodeObject::Helpers, Helpers::BaseHelpers, Helpers::DocumentationHelpers
Defined in:
lib/pry/method.rb,
lib/pry/method/patcher.rb,
lib/pry/method/disowned.rb,
lib/pry/method/weird_method_locator.rb

Overview

This class wraps the normal Method and UnboundMethod classes to provide extra functionality useful to Pry.

Direct Known Subclasses

Disowned

Defined Under Namespace

Classes: Disowned, Patcher, WeirdMethodLocator

Class Method Summary collapse

Instance Method Summary collapse

Methods included from Helpers::BaseHelpers

colorize_code, colorize_code, command_dependencies_met?, command_dependencies_met?, find_command, find_command, heading, heading, highlight, highlight, jruby?, jruby?, jruby_19?, jruby_19?, mri?, mri?, mri_19?, mri_19?, mri_20?, mri_20?, mri_21?, mri_21?, mri_2?, mri_2?, not_a_real_file?, not_a_real_file?, rbx?, rbx?, safe_send, safe_send, silence_warnings, silence_warnings, stagger_output, stagger_output, use_ansi_codes?, use_ansi_codes?, windows?, windows?, windows_ansi?, windows_ansi?

Methods included from CodeObject::Helpers

#c_method?, #command?, #module_with_yard_docs?, #real_method_object?

Methods included from Helpers::DocumentationHelpers

#get_comment_content, get_comment_content, process_comment_markup, #process_comment_markup, #process_rdoc, process_rdoc, #process_yardoc, process_yardoc, process_yardoc_tag, #process_yardoc_tag, #strip_comments_from_c_code, strip_comments_from_c_code, #strip_leading_whitespace, strip_leading_whitespace

Constructor Details

#initialize(method, known_info = {}) ⇒ Pry::Method

A new instance of Pry::Method wrapping the given ::Method, UnboundMethod, or Proc.

Parameters:

  • method (::Method, UnboundMethod, Proc)
  • known_info (Hash) (defaults to: {})

    Can be used to pre-cache expensive to compute stuff.



236
237
238
239
# File 'lib/pry/method.rb', line 236

def initialize(method, known_info={})
  @method = method
  @visibility = known_info[:visibility]
end

Dynamic Method Handling

This class handles dynamic methods through the method_missing method

#method_missing(method_name, *args, &block) ⇒ Object

Delegate any unknown calls to the wrapped method.



469
470
471
# File 'lib/pry/method.rb', line 469

def method_missing(method_name, *args, &block)
  @method.send(method_name, *args, &block)
end

Class Method Details

.all_from_class(klass, include_super = true) ⇒ Array[Pry::Method]

Get all of the instance methods of a Class or Module

Parameters:

  • klass (Class, Module)
  • include_super (Boolean) (defaults to: true)

    Whether to include methods from ancestors.

Returns:



142
143
144
145
146
147
148
# File 'lib/pry/method.rb', line 142

def all_from_class(klass, include_super=true)
  %w(public protected private).flat_map do |visibility|
    safe_send(klass, :#{visibility}_instance_methods", include_super).map do |method_name|
      new(safe_send(klass, :instance_method, method_name), :visibility => visibility.to_sym)
    end
  end
end

.all_from_common(obj, method_type = nil, include_super = true) ⇒ Object

Deprecated.

please use #all_from_obj instead. the method_type argument is ignored.



169
170
171
# File 'lib/pry/method.rb', line 169

def all_from_common(obj, method_type = nil, include_super=true)
  all_from_obj(obj, include_super)
end

.all_from_obj(obj, include_super = true) ⇒ Array[Pry::Method]

Get all of the methods on an Object

Parameters:

  • obj (Object)
  • include_super (Boolean) (defaults to: true)

    indicates whether or not to include methods from ancestors.

Returns:



160
161
162
# File 'lib/pry/method.rb', line 160

def all_from_obj(obj, include_super=true)
  all_from_class(singleton_class_of(obj), include_super)
end

.from_binding(b) ⇒ Pry::Method?

Given a Binding, try to extract the ::Method it originated from and use it to instantiate a Pry::Method. Return nil if this isn't possible.

Parameters:

  • b (Binding)

Returns:



74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
# File 'lib/pry/method.rb', line 74

def from_binding(b)
  meth_name = b.eval('::Kernel.__method__')
  if [:__script__, nil].include?(meth_name)
    nil
  else
    method = begin
               if Object === b.eval('self')
                 new(Kernel.instance_method(:method).bind(b.eval("self")).call(meth_name))
               else
                 new(b.eval('class << self; self; end.instance_method(::Kernel.__method__).bind(self)'))
               end
             rescue NameError, NoMethodError
               Disowned.new(b.eval('self'), meth_name.to_s)
             end

    if WeirdMethodLocator.weird_method?(method, b)
      WeirdMethodLocator.new(method, b).get_method || method
    else
      method
    end
  end
end

.from_class(klass, name, target = TOPLEVEL_BINDING) ⇒ Pry::Method? Also known as: from_module

Given a Class or Module and the name of a method, try to instantiate a Pry::Method containing the instance method of that name. Return nil if no such method exists.

Parameters:

  • klass (Class, Module)
  • name (String)
  • target (Binding) (defaults to: TOPLEVEL_BINDING)

    The binding where the method is looked up.

Returns:



121
122
123
# File 'lib/pry/method.rb', line 121

def from_class(klass, name, target=TOPLEVEL_BINDING)
  new(lookup_method_via_binding(klass, name, :instance_method, target)) rescue nil
end

.from_obj(obj, name, target = TOPLEVEL_BINDING) ⇒ Pry::Method?

Given an object and the name of a method, try to instantiate a Pry::Method containing the method of that name bound to that object. Return nil if no such method exists.

Parameters:

  • obj (Object)
  • name (String)
  • target (Binding) (defaults to: TOPLEVEL_BINDING)

    The binding where the method is looked up.

Returns:



134
135
136
# File 'lib/pry/method.rb', line 134

def from_obj(obj, name, target=TOPLEVEL_BINDING)
  new(lookup_method_via_binding(obj, name, :method, target)) rescue nil
end

.from_str(name, target = TOPLEVEL_BINDING, options = {}) ⇒ Pry::Method?

Given a string representing a method name and optionally a binding to search in, find and return the requested method wrapped in a Pry::Method instance.

Parameters:

  • name (String)

    The name of the method to retrieve.

  • target (Binding) (defaults to: TOPLEVEL_BINDING)

    The context in which to search for the method.

  • options (Hash) (defaults to: {})

Options Hash (options):

  • :instance (Boolean)

    Look for an instance method if name doesn't contain any context.

  • :methods (Boolean)

    Look for a bound/singleton method if name doesn't contain any context.

Returns:

  • (Pry::Method, nil)

    A Pry::Method instance containing the requested method, or nil if name is nil or no method could be located matching the parameters.



42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
# File 'lib/pry/method.rb', line 42

def from_str(name, target=TOPLEVEL_BINDING, options={})
  if name.nil?
    nil
  elsif name.to_s =~ /(.+)\#(\S+)\Z/
    context, meth_name = $1, $2
    from_module(target.eval(context), meth_name, target)
  elsif name.to_s =~ /(.+)(\[\])\Z/
    context, meth_name = $1, $2
    from_obj(target.eval(context), meth_name, target)
  elsif name.to_s =~ /(.+)(\.|::)(\S+)\Z/
    context, meth_name = $1, $3
    from_obj(target.eval(context), meth_name, target)
  elsif options[:instance]
    from_module(target.eval("self"), name, target)
  elsif options[:methods]
    from_obj(target.eval("self"), name, target)
  else
    from_str(name, target, :instance => true) or
      from_str(name, target, :methods => true)
  end

rescue Pry::RescuableException
  nil
end

.instance_method_definition?(name, definition_line) ⇒ Boolean

Returns:

  • (Boolean)


205
206
207
# File 'lib/pry/method.rb', line 205

def instance_method_definition?(name, definition_line)
  /^define_method\(?\s*[:\"\']#{Regexp.escape(name)}|^def\s*#{Regexp.escape(name)}/ =~ definition_line.strip
end

.instance_resolution_order(klass) ⇒ Array[Class, Module]

Get every Class and Module, in order, that will be checked when looking for methods on instances of the given Class or Module. This does not treat singleton classes of classes specially.

Parameters:

  • klass (Class, Module)

Returns:

  • (Array[Class, Module])


191
192
193
194
# File 'lib/pry/method.rb', line 191

def instance_resolution_order(klass)
  # include klass in case it is a singleton class,
  ([klass] + Pry::Method.safe_send(klass, :ancestors)).uniq
end

.lookup_method_via_binding(obj, method_name, method_type, target = TOPLEVEL_BINDING) ⇒ Method, UnboundMethod

In order to support 2.0 Refinements we need to look up methods inside the relevant Binding.

Parameters:

  • obj (Object)

    The owner/receiver of the method.

  • method_name (Symbol)

    The name of the method.

  • method_type (Symbol)

    The type of method: :method or :instance_method

  • target (Binding) (defaults to: TOPLEVEL_BINDING)

    The binding where the method is looked up.

Returns:

  • (Method, UnboundMethod)

    The 'refined' method object.



104
105
106
107
108
109
110
111
# File 'lib/pry/method.rb', line 104

def lookup_method_via_binding(obj, method_name, method_type, target=TOPLEVEL_BINDING)
  Pry.current[:obj] = obj
  Pry.current[:name] = method_name
  receiver = obj.is_a?(Module) ? "Module" : "Kernel"
  target.eval("::#{receiver}.instance_method(:#{method_type}).bind(Pry.current[:obj]).call(Pry.current[:name])")
ensure
  Pry.current[:obj] = Pry.current[:name] = nil
end

.method_definition?(name, definition_line) ⇒ Boolean

Returns:

  • (Boolean)


196
197
198
199
# File 'lib/pry/method.rb', line 196

def method_definition?(name, definition_line)
  singleton_method_definition?(name, definition_line) ||
    instance_method_definition?(name, definition_line)
end

.resolution_order(obj) ⇒ Array[Class, Module]

Get every Class and Module, in order, that will be checked when looking for an instance method to call on this object.

Parameters:

Returns:

  • (Array[Class, Module])


177
178
179
180
181
182
183
184
# File 'lib/pry/method.rb', line 177

def resolution_order(obj)
  if Class === obj
    singleton_class_resolution_order(obj) + instance_resolution_order(Class)
  else
    klass = singleton_class_of(obj) rescue obj.class
    instance_resolution_order(klass)
  end
end

.singleton_class_of(obj) ⇒ Object



222
223
224
225
226
227
228
# File 'lib/pry/method.rb', line 222

def singleton_class_of(obj)
  begin
    class << obj; self; end
  rescue TypeError # can't define singleton. Fixnum, Symbol, Float, ...
    obj.class
  end
end

.singleton_class_resolution_order(klass) ⇒ Object

Get the singleton classes of superclasses that could define methods on the given class object, and any modules they include. If a module is included at multiple points in the ancestry, only the lowest copy will be returned.



213
214
215
216
217
218
219
220
# File 'lib/pry/method.rb', line 213

def singleton_class_resolution_order(klass)
  ancestors = Pry::Method.safe_send(klass, :ancestors)
  resolution_order = ancestors.grep(Class).flat_map do |anc|
    [singleton_class_of(anc), *singleton_class_of(anc).included_modules]
  end

  resolution_order.reverse.uniq.reverse - Class.included_modules
end

.singleton_method_definition?(name, definition_line) ⇒ Boolean

Returns:

  • (Boolean)


201
202
203
# File 'lib/pry/method.rb', line 201

def singleton_method_definition?(name, definition_line)
  /^define_singleton_method\(?\s*[:\"\']#{Regexp.escape(name)}|^def\s*self\.#{Regexp.escape(name)}/ =~ definition_line.strip
end

Instance Method Details

#==(obj) ⇒ Boolean

Returns:

  • (Boolean)


447
448
449
450
451
452
453
# File 'lib/pry/method.rb', line 447

def ==(obj)
  if obj.is_a? Pry::Method
    obj == @method
  else
    @method == obj
  end
end

#alias?Boolean

Returns Is the method definitely an alias?

Returns:

  • (Boolean)

    Is the method definitely an alias?



442
443
444
# File 'lib/pry/method.rb', line 442

def alias?
  name != original_name
end

#aliasesArray<String>

Returns All known aliases for the method.

Returns:

  • (Array<String>)

    All known aliases for the method.



425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
# File 'lib/pry/method.rb', line 425

def aliases
  owner = @method.owner
  # Avoid using `to_sym` on {Method#name}, which returns a `String`, because
  # it won't be garbage collected.
  name = @method.name

  all_methods_to_compare = owner.instance_methods | owner.private_instance_methods
  alias_list = all_methods_to_compare.combination(2).select do |pair|
    pair.include?(name) &&
      owner.instance_method(pair.first) == owner.instance_method(pair.last)
  end.flatten
  alias_list.delete(name)

  alias_list.map(&:to_s)
end

#bound_method?Boolean

Returns Whether the method is bound.

Returns:

  • (Boolean)

    Whether the method is bound.



410
411
412
# File 'lib/pry/method.rb', line 410

def bound_method?
  is_a?(::Method)
end

#c_sourceObject (private)



524
525
526
527
528
529
# File 'lib/pry/method.rb', line 524

def c_source
  info = pry_doc_info
  if info and info.source
    strip_comments_from_c_code(info.source)
  end
end

#commentObject



473
474
475
# File 'lib/pry/method.rb', line 473

def comment
  Pry::Code.from_file(source_file).comment_describing(source_line)
end

#docString?

Returns The documentation for the method, or nil if it's unavailable.

Returns:

  • (String, nil)

    The documentation for the method, or nil if it's unavailable.



300
301
302
303
304
305
306
307
308
# File 'lib/pry/method.rb', line 300

def doc
  @doc ||= case source_type
    when :c
      info = pry_doc_info
      info.docstring if info
    when :ruby
      get_comment_content(comment)
    end
end

#dynamically_defined?Boolean

Returns Was the method defined outside a source file?

Returns:

  • (Boolean)

    Was the method defined outside a source file?



400
401
402
# File 'lib/pry/method.rb', line 400

def dynamically_defined?
  !!(source_file and source_file =~ /(\(.*\))|<.*>/)
end

#is_a?(klass) ⇒ Boolean Also known as: kind_of?

Parameters:

  • klass (Class)

Returns:

  • (Boolean)


457
458
459
# File 'lib/pry/method.rb', line 457

def is_a?(klass)
  klass == Pry::Method or @method.is_a?(klass)
end

#method_name_from_first_line(first_ln) ⇒ String? (private)

Parameters:

  • first_ln (String)

    The first line of a method definition.

Returns:

  • (String, nil)


510
511
512
513
514
515
516
517
518
519
520
521
522
# File 'lib/pry/method.rb', line 510

def method_name_from_first_line(first_ln)
  return nil if first_ln.strip !~ /^def /

  tokens = CodeRay.scan(first_ln, :ruby)
  tokens = tokens.tokens.each_slice(2) if tokens.respond_to?(:tokens)
  tokens.each_cons(2) do |t1, t2|
    if t2.last == :method || t2.last == :ident && t1 == [".", :operator]
      return t2.first
    end
  end

  nil
end

#nameString

Get the name of the method as a String, regardless of the underlying Method#name type.

Returns:

  • (String)


243
244
245
# File 'lib/pry/method.rb', line 243

def name
  @method.name.to_s
end

#name_with_ownerString

Get the name of the method including the class on which it was defined.

Examples:

method(:puts).method_name
=> "Kernel.puts"

Returns:

  • (String)


270
271
272
# File 'lib/pry/method.rb', line 270

def name_with_owner
  "#{wrapped_owner.method_prefix}#{name}"
end

#original_nameString?

Returns The original name the method was defined under, before any aliasing, or nil if it can't be determined.

Returns:

  • (String, nil)

    The original name the method was defined under, before any aliasing, or nil if it can't be determined.



394
395
396
397
# File 'lib/pry/method.rb', line 394

def original_name
  return nil if source_type != :ruby
  method_name_from_first_line(source.lines.first)
end

#pry_doc_infoYARD::CodeObjects::MethodObject (private)

Returns:

  • (YARD::CodeObjects::MethodObject)

Raises:

  • (CommandError)

    when the method can't be found or pry-doc isn't installed.



481
482
483
484
485
486
487
488
489
490
491
# File 'lib/pry/method.rb', line 481

def pry_doc_info
  if Pry.config.has_pry_doc
    Pry::MethodInfo.info_for(@method) or raise CommandError, "Cannot locate this method: #{name}. (source_location returns nil)"
  else
    fail_msg = "Cannot locate this method: #{name}."
    if mri?
      fail_msg += ' Try `gem-install pry-doc` to get access to Ruby Core documentation.'
    end
    raise CommandError, fail_msg
  end
end

#pry_method?Boolean

Returns Was the method defined within the Pry REPL?

Returns:

  • (Boolean)

    Was the method defined within the Pry REPL?



420
421
422
# File 'lib/pry/method.rb', line 420

def pry_method?
  source_file == Pry.eval_path
end

#redefine(source) ⇒ Object

Update the live copy of the method's source.



285
286
287
288
# File 'lib/pry/method.rb', line 285

def redefine(source)
  Patcher.new(self).patch_in_ram source
  Pry::Method(owner.instance_method(name))
end

#respond_to?(method_name) ⇒ Boolean

Parameters:

  • method_name (String, Symbol)

Returns:

  • (Boolean)


464
465
466
# File 'lib/pry/method.rb', line 464

def respond_to?(method_name)
  super or @method.respond_to?(method_name)
end

#ruby_sourceObject (private)

Raises:

  • (SourceNotFoundError)


531
532
533
534
535
536
537
538
539
540
541
542
543
544
# File 'lib/pry/method.rb', line 531

def ruby_source
  # clone of MethodSource.source_helper that knows to use our
  # hacked version of source_location for rbx core methods, and
  # our input buffer for methods defined in (pry)
  file, line = *source_location
  raise SourceNotFoundError, "Could not locate source for #{name_with_owner}!" unless file

  begin
    code = Pry::Code.from_file(file).expression_at(line)
  rescue SyntaxError => e
    raise MethodSource::SourceNotFoundError.new(e.message)
  end
  strip_leading_whitespace(code)
end

#signatureString

Returns A representation of the method's signature, including its name and parameters. Optional and "rest" parameters are marked with * and block parameters with &. If the parameter names are unavailable, they're given numbered names instead. Paraphrased from awesome_print gem.

Returns:

  • (String)

    A representation of the method's signature, including its name and parameters. Optional and "rest" parameters are marked with * and block parameters with &. If the parameter names are unavailable, they're given numbered names instead. Paraphrased from awesome_print gem.



360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
# File 'lib/pry/method.rb', line 360

def signature
  if respond_to?(:parameters)
    args = parameters.inject([]) do |arr, (type, name)|
      name ||= (type == :block ? 'block' : "arg#{arr.size + 1}")
      arr << case type
             when :req   then name.to_s
             when :opt   then "#{name}=?"
             when :rest  then "*#{name}"
             when :block then "&#{name}"
             else '?'
             end
    end
  else
    args = (1..arity.abs).map { |i| "arg#{i}" }
    args[-1] = "*#{args[-1]}" if arity < 0
  end

  "#{name}(#{args.join(', ')})"
end

#singleton_method?Boolean

Returns Whether the method is a singleton method.

Returns:

  • (Boolean)

    Whether the method is a singleton method.



415
416
417
# File 'lib/pry/method.rb', line 415

def singleton_method?
  wrapped_owner.singleton_class?
end

#sourceString?

Returns The source code of the method, or nil if it's unavailable.

Returns:

  • (String, nil)

    The source code of the method, or nil if it's unavailable.



275
276
277
278
279
280
281
282
# File 'lib/pry/method.rb', line 275

def source
  @source ||= case source_type
              when :c
                c_source
              when :ruby
                ruby_source
              end
end

#source?Boolean

Can we get the source code for this method?

Returns:

  • (Boolean)


292
293
294
295
296
# File 'lib/pry/method.rb', line 292

def source?
  !!source
rescue MethodSource::SourceNotFoundError
  false
end

#source_fileString?

Returns The name of the file the method is defined in, or nil if the filename is unavailable.

Returns:

  • (String, nil)

    The name of the file the method is defined in, or nil if the filename is unavailable.



318
319
320
321
322
323
324
325
326
327
# File 'lib/pry/method.rb', line 318

def source_file
  if source_location.nil?
    if !rbx? and source_type == :c
      info = pry_doc_info
      info.file if info
    end
  else
    source_location.first
  end
end

#source_lineFixnum?

Returns The line of code in source_file which begins the method's definition, or nil if that information is unavailable.

Returns:

  • (Fixnum, nil)

    The line of code in source_file which begins the method's definition, or nil if that information is unavailable.



331
332
333
# File 'lib/pry/method.rb', line 331

def source_line
  source_location.nil? ? nil : source_location.last
end

#source_rangeRange?

Returns The range of lines in source_file which contain the method's definition, or nil if that information is unavailable.

Returns:

  • (Range, nil)

    The range of lines in source_file which contain the method's definition, or nil if that information is unavailable.



337
338
339
# File 'lib/pry/method.rb', line 337

def source_range
  source_location.nil? ? nil : (source_line)..(source_line + source.lines.count - 1)
end

#source_typeSymbol

Returns The source type of the method. The options are :ruby for Ruby methods or :c for methods written in C.

Returns:

  • (Symbol)

    The source type of the method. The options are :ruby for Ruby methods or :c for methods written in C.



312
313
314
# File 'lib/pry/method.rb', line 312

def source_type
  source_location.nil? ? :c : :ruby
end

#super(times = 1) ⇒ Pry::Method?

Returns The wrapped method that is called when you use "super" in the body of this method.

Returns:

  • (Pry::Method, nil)

    The wrapped method that is called when you use "super" in the body of this method.



382
383
384
385
386
387
388
389
390
# File 'lib/pry/method.rb', line 382

def super(times=1)
  if UnboundMethod === @method
    sup = super_using_ancestors(Pry::Method.instance_resolution_order(owner), times)
  else
    sup = super_using_ancestors(Pry::Method.resolution_order(receiver), times)
    sup &&= sup.bind(receiver)
  end
  Pry::Method.new(sup) if sup
end

#super_using_ancestors(ancestors, times = 1) ⇒ Method (private)

Returns The unwrapped super-method

Parameters:

  • ancestors (Class, Module)

    The ancestors to investigate

Returns:

  • (Method)

    The unwrapped super-method



495
496
497
498
499
500
501
502
503
504
505
506
# File 'lib/pry/method.rb', line 495

def super_using_ancestors(ancestors, times=1)
  next_owner = self.owner
  times.times do
    i = ancestors.index(next_owner) + 1
    while ancestors[i] && !(ancestors[i].method_defined?(name) || ancestors[i].private_method_defined?(name))
      i += 1
    end
    next_owner = ancestors[i] or return nil
  end

  safe_send(next_owner, :instance_method, name) rescue nil
end

#unbound_method?Boolean

Returns Whether the method is unbound.

Returns:

  • (Boolean)

    Whether the method is unbound.



405
406
407
# File 'lib/pry/method.rb', line 405

def unbound_method?
  is_a?(::UnboundMethod)
end

#undefined?Boolean

Is the method undefined? (aka Disowned)

Returns:

  • (Boolean)

    false



261
262
263
# File 'lib/pry/method.rb', line 261

def undefined?
  false
end

#visibilitySymbol

Returns The visibility of the method. May be :public, :protected, or :private.

Returns:

  • (Symbol)

    The visibility of the method. May be :public, :protected, or :private.



343
344
345
346
347
348
349
350
351
352
353
# File 'lib/pry/method.rb', line 343

def visibility
 @visibility ||= if owner.public_instance_methods.any? { |m| m.to_s == name }
                   :public
                 elsif owner.protected_instance_methods.any? { |m| m.to_s == name }
                   :protected
                 elsif owner.private_instance_methods.any? { |m| m.to_s == name }
                   :private
                 else
                   :none
                 end
end

#wrappedMethod, ...

Get underlying object wrapped by this Pry::Method instance

Returns:

  • (Method, UnboundMethod, Proc)


255
256
257
# File 'lib/pry/method.rb', line 255

def wrapped
  @method
end

#wrapped_ownerPry::Module

Get the owner of the method as a Pry::Module

Returns:

  • (Pry::Module)


249
250
251
# File 'lib/pry/method.rb', line 249

def wrapped_owner
  @wrapped_owner ||= Pry::WrappedModule.new(owner)
end