peeky 0.0.14 → 0.0.28

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 28af40c7ccec4e9da59512a6fbac9a111768d5466c17a9a0fc0003928fa59191
4
- data.tar.gz: '087aefb7db2766131766ab7cc9346449896cbec13ec14a583f96b3971da29df8'
3
+ metadata.gz: f5bfa72308dbaa677a774831ef7323b1a6b7756589714b068edab839232e96c1
4
+ data.tar.gz: c20a0d04a9ef69d8f77d7c506ddd45560294a4e9b0b7ec7ffeb33c6665b6a3f6
5
5
  SHA512:
6
- metadata.gz: 6fd1164f74cd0f4b39a60b758372d771105147bd95e5032731d74c398862b60f748ea1b9b12ce4a92ff0857a0ae3d635db88781ce5390bc222156ca3625ed73e
7
- data.tar.gz: 2c89b203b742301aa4834077bf56d60b6a412a753cff3d3c223dd2a86fb6a95d68aeff05f770d0b977760c94a6afea47f83fdd922796d6bb25046666a384a4ea
6
+ metadata.gz: '0070992885f6a7a5a19acb3d62fef9e5ce3d116b35c0436185fe3304293c7831bb6c9652704c43985842854bba7472733bb10b2cd26f055b9893dedecae27604'
7
+ data.tar.gz: 2312202e390a5ad6478aa124f94634627b65d7a69f0e0b725091907d7bddc10040a524b7eaf784e0bf37c74ab030228a74a8d1a319f810516308c7dc83c985ea
@@ -0,0 +1,31 @@
1
+ # This workflow will download a prebuilt Ruby version, install dependencies and run tests with Rake
2
+ # For more information see: https://github.com/marketplace/actions/setup-ruby-jruby-and-truffleruby
3
+
4
+ name: Ruby
5
+
6
+ on:
7
+ push:
8
+ branches: [ master ]
9
+ pull_request:
10
+ branches: [ master ]
11
+
12
+ jobs:
13
+ test:
14
+
15
+ runs-on: ubuntu-latest
16
+
17
+ steps:
18
+ - uses: actions/checkout@v2
19
+ - name: Set up Ruby
20
+ # To automatically get bug fixes and new Ruby versions for ruby/setup-ruby,
21
+ # change this to (see https://github.com/ruby/setup-ruby#versioning):
22
+ # uses: ruby/setup-ruby@v1
23
+ uses: ruby/setup-ruby@ec106b438a1ff6ff109590de34ddc62c540232e0
24
+ with:
25
+ ruby-version: 2.6
26
+ - name: Install dependencies
27
+ run: bundle install
28
+ - name: Run tests
29
+ run: bundle exec rspec
30
+ - name: Run rubocop
31
+ run: bundle exec rubocop
data/.gitignore CHANGED
@@ -44,3 +44,5 @@ Gemfile.lock
44
44
 
45
45
  # ByeBug history
46
46
  .byebug_history
47
+
48
+ *.gem
@@ -4,8 +4,26 @@ AllCops:
4
4
  NewCops: enable
5
5
  Exclude:
6
6
  - "_/**/*"
7
+ - "lib/peeky/example/yard_sample.rb"
7
8
 
8
9
  # My Preferences - Start
10
+ Naming/MemoizedInstanceVariableName:
11
+ Enabled: false
12
+
13
+ Style/EmptyMethod:
14
+ Exclude:
15
+ - "**/spec/**/*"
16
+ Metrics/ParameterLists:
17
+ Exclude:
18
+ - "**/spec/**/*"
19
+ Layout/EmptyLineBetweenDefs:
20
+ Exclude:
21
+ - "**/spec/**/*"
22
+
23
+ Lint/AmbiguousBlockAssociation:
24
+ Exclude:
25
+ - "**/spec/**/*"
26
+
9
27
  Style/AccessorGrouping:
10
28
  Enabled: false
11
29
 
@@ -16,6 +34,7 @@ Layout/SpaceBeforeComma:
16
34
  Metrics/BlockLength:
17
35
  Exclude:
18
36
  - "**/spec/*"
37
+ - "*.gemspec"
19
38
  ExcludedMethods:
20
39
  - configure
21
40
  - context
@@ -21,6 +21,10 @@ Gemspec/RequiredRubyVersion:
21
21
  Exclude:
22
22
  - 'peeky.gemspec'
23
23
 
24
+ Metrics/BlockLength:
25
+ Exclude:
26
+ - 'peeky.gemspec'
27
+
24
28
  # Offense count: 1
25
29
  # Cop supports --auto-correct.
26
30
  # Configuration parameters: EnforcedStyle.
@@ -55,7 +55,7 @@ further defined and clarified by project maintainers.
55
55
  ## Enforcement
56
56
 
57
57
  Instances of abusive, harassing, or otherwise unacceptable behavior may be
58
- reported by contacting the project team at david.cruwys@bugcrowd.com. All
58
+ reported by contacting the project team at david@ideasmne.com.au. All
59
59
  complaints will be reviewed and investigated and will result in a response that
60
60
  is deemed necessary and appropriate to the circumstances. The project team is
61
61
  obligated to maintain confidentiality with regard to the reporter of an incident.
data/Gemfile CHANGED
@@ -5,13 +5,16 @@ source 'https://rubygems.org'
5
5
  # Specify your gem's dependencies in poc_github_ap.gemspec
6
6
  gemspec
7
7
 
8
+ # group :development do
9
+ # # pry on steroids
10
+ # gem 'pry-coolline', github: 'owst/pry-coolline', branch: 'support_new_pry_config_api'
11
+ # gem 'jazz_fingers'
12
+ # end
13
+
8
14
  group :development, :test do
9
15
  gem 'guard-bundler'
10
16
  gem 'guard-rspec'
11
17
  gem 'guard-rubocop'
12
- # pry on steroids
13
- gem 'pry-coolline', github: 'owst/pry-coolline', branch: 'support_new_pry_config_api'
14
- gem 'jazz_fingers'
15
18
  gem 'rake', '~> 12.0'
16
19
  # this is used for cmdlets 'self-executing gems'
17
20
  gem 'rake-compiler'
data/Guardfile CHANGED
@@ -23,8 +23,8 @@ group :green_pass_then_cop, halt_on_fail: true do
23
23
  watch(%r{^lib/peeky/commands/(.+)\.rb$}) { |m| "spec/unit/commands/#{m[1]}_spec.rb" }
24
24
  end
25
25
 
26
- guard :rubocop, all_on_start: false, cli: ['--format', 'clang'] do
27
- watch(%r{.+\.rb$})
28
- watch(%r{(?:.+/)?\.rubocop(?:_todo)?\.yml$}) { |m| File.dirname(m[0]) }
29
- end
26
+ # guard :rubocop, all_on_start: false, cli: ['--format', 'clang'] do
27
+ # watch(%r{.+\.rb$})
28
+ # watch(%r{(?:.+/)?\.rubocop(?:_todo)?\.yml$}) { |m| File.dirname(m[0]) }
29
+ # end
30
30
  end
data/README.md CHANGED
@@ -1,40 +1,9 @@
1
- # ToDo
2
-
3
- * Manually create each file using the template system
4
- - Models
5
- - [Done] ParameterInfo
6
- - [Done] AttrInfo
7
- - [Done] ClassInfo
8
- - [Done] MethodInfo
9
- - Create predicates
10
- - [Done] attr_reader_predicate
11
- - [Done] attr_writer_predicate
12
- - Create renderers
13
- - [Done] method_call_minimum_params_render
14
- - [Done] method_signature_render
15
- - [Done] method_signature_with_debug_render
16
- - [Done] class_interface_render
17
- - [Done] Recreate peeky
18
- - [Done] Symlink KlueLess files
19
- - [Done] Hot fix after each section
20
- - [Done] Make sure the klueless files follow a natural structure
21
- - [Done] Push peeky to Ruby Gems
22
- - Build out the readme file
23
- - Build out the stories
24
- - Back compare templates vis definitions
25
- - Auto create .template folder with copied definitions
26
-
27
-
28
1
  # Peeky
29
2
 
30
3
  > Peeky is a Ruby GEM for peaking into ruby classes and extracting meta
31
4
 
32
- Welcome to your new ruby gem! In this directory, you'll find the files you need to be able to package up your Ruby library into a gem. Put your Ruby code in the file `lib/peeky`.
33
-
34
5
  When using the source code for this gem, start by running `bin/setup` to install locally or `bundle install`
35
6
 
36
- To experiment with that code, run `bin/console` for an interactive prompt or run `exe/peeky` to see a list of commands.
37
-
38
7
  ## Installation
39
8
 
40
9
  Add this line to your application's Gemfile:
@@ -57,6 +26,17 @@ gem install peeky
57
26
 
58
27
  ## Stories
59
28
 
29
+ ### Main Story
30
+
31
+ As a Ruby Developer, I should be able to Reverse engineer classes and methods, so that I can document and understand them
32
+
33
+ See all [stories](./file.STORIES.html)
34
+
35
+ ### Featured Stories
36
+
37
+ - As a Developer, I should be able to interrogate class instance information, so that I can reverse engineer a ruby class
38
+ - As a Developer, I can render method with minimal parameter calls, So that I know the minimum parameters when calling a method
39
+ - As a Developer, I can render a class with instance attributes and methods, So that I can quickly mock out an entire class
60
40
 
61
41
  ## Usage
62
42
 
@@ -78,7 +58,7 @@ The gem is available as open source under the terms of the [MIT License](https:/
78
58
 
79
59
  ## Code of Conduct
80
60
 
81
- Everyone interacting in the Peeky project’s codebases, issue trackers, chat rooms and mailing lists is expected to follow the [code of conduct](https://github.com/[USERNAME]/peeky/blob/master/CODE_OF_CONDUCT.md).
61
+ Everyone interacting in the Peeky project’s codebases, issue trackers, chat rooms and mailing lists is expected to follow the.
82
62
 
83
63
  ## Copyright
84
64
 
@@ -0,0 +1,83 @@
1
+ # Peeky
2
+
3
+ > Peeky is a Ruby GEM for peaking into ruby classes and extracting meta
4
+
5
+ As a Ruby Developer, I should be able to Reverse engineer classes and methods, so that I can document and understand them
6
+
7
+ ## Development rader
8
+
9
+
10
+ ### Tasks next on list
11
+
12
+ As a Developer, I can render a class with RDoc documentation, so that I do not have to manually type RDoc references
13
+
14
+ - Add simplified API with examples
15
+ - Start documenting usage instructions
16
+
17
+ As a Developer, I can use Peeky with a simple API, so that I use this GEM quickly
18
+
19
+ - Add simplified API with examples
20
+ - Start documenting usage instructions
21
+
22
+ As a Developer, I can quickly build requirements, so that I can document project features
23
+
24
+ - Add support for backlog stories and tasks
25
+ - Add usage instructions
26
+
27
+
28
+
29
+ ## Stories and tasks
30
+
31
+ ### Stories - completed
32
+
33
+ As a David, I can edify Karin, because she is cool
34
+
35
+ - karin_is_awesome
36
+ - i_am_very_grateful_for_karin
37
+ - karin_the_beautiful
38
+
39
+ As a Developer, I can render a class with instance attributes and methods, So that I can quickly mock out an entire class
40
+
41
+ - Render: Class Interface
42
+
43
+ As a Developer, I can render method signature with debug code, So that mock out a method with parameter logging
44
+
45
+ - Render: Method signature with debug code
46
+
47
+ As a Developer, I can see the method signature of a method, So that I understand it's parameters
48
+
49
+ - Render: Method Signature in compact format
50
+
51
+ As a Developer, I can render method with minimal parameter calls, So that I know the minimum parameters when calling a method
52
+
53
+ - Render: Simple instance method calls with minimum parameters
54
+
55
+ As a Developer, I can tell if a method is attr_*, so that I can format methods using attr_* notation
56
+
57
+ - Attr Writer Predicate will match true if the method info could be considered a valid attr_writer
58
+ - Attr Writer Predicate will match true if the method info could be considered a valid attr_writer
59
+
60
+ As a Developer, I should be able to interrogate class instance information, so that I can reverse engineer a ruby class
61
+
62
+ - ParameterInfo model to store information about parameters on a method
63
+ - MethodInfo model to store signature of a ruby instance method
64
+ - AttrInfo is a container that represents attr_reader, attr_writer or attr_accessor by storying 1 or 2 MethodInfo
65
+ - ClassInfo stores information about a ruby class. Only support instance methods
66
+
67
+
68
+ ##$ Tasks - completed
69
+
70
+ Setup GitHub Action (test and lint)
71
+
72
+ - Setup Rspec action
73
+ - Setup RuboCop action
74
+
75
+ Setup new Ruby GEM
76
+
77
+ - Build out a standard GEM structure
78
+ - Add semantic versioning
79
+ - Add Rspec unit testing framework
80
+ - Add RuboCop linting
81
+ - Add Guard for automatic watch and test
82
+ - Add GitFlow support
83
+ - Add GitHub Repository
@@ -2,6 +2,8 @@
2
2
 
3
3
  require 'peeky/version'
4
4
 
5
+ require 'peeky/api'
6
+
5
7
  require 'peeky/attr_info'
6
8
  require 'peeky/class_info'
7
9
  require 'peeky/method_info'
@@ -11,6 +13,7 @@ require 'peeky/predicates/attr_reader_predicate'
11
13
  require 'peeky/predicates/attr_writer_predicate'
12
14
 
13
15
  require 'peeky/renderer/class_interface_render'
16
+ require 'peeky/renderer/class_interface_yard_render'
14
17
  require 'peeky/renderer/method_call_minimum_params_render'
15
18
  require 'peeky/renderer/method_signature_render'
16
19
  require 'peeky/renderer/method_signature_with_debug_render'
@@ -0,0 +1,70 @@
1
+ # frozen_string_literal: true
2
+
3
+ # Peeky module provides access to the API via the
4
+ # module method Peeky.api
5
+ module Peeky
6
+ class << self
7
+ attr_accessor :api
8
+ end
9
+
10
+ # API has factory and creational patterns for easy usage
11
+ # of the Peeky reflection system
12
+ class Api
13
+ # Build a {Peeky::ClassInfo} structure based around a
14
+ # ruby class instance.
15
+ #
16
+ # ClassInfo stores information about the instance of a
17
+ # class that is passed in including methods, attr_accessors
18
+ # attr_readers and attr_writers.
19
+ def build_class_info(instance)
20
+ Peeky::ClassInfo.new(instance)
21
+ end
22
+
23
+ # Render a class using a predefined class renderer
24
+ def render_class(render_key, class_info: nil, instance: nil, **_opts)
25
+ raise 'Call render_class with class_info OR instance.' if class_info.nil? && instance.nil?
26
+ raise 'Call render_class with class_info OR instance, these parameters are mutually exclusive' if !class_info.nil? && !instance.nil?
27
+
28
+ renderer = class_renderer(render_key)
29
+
30
+ class_info = Peeky::ClassInfo.new(instance) if class_info.nil?
31
+
32
+ renderer.new(class_info).render
33
+ end
34
+
35
+ # Get a method renderer by :key
36
+ #
37
+ # TODO: Refactor to a configurable system
38
+ def method_renderer(key)
39
+ case key
40
+ when :signature
41
+ Peeky::Renderer::MethodSignatureRender
42
+ when :signature_with_debug
43
+ Peeky::Renderer::MethodSignatureWithDebugRender
44
+ when :call_minimum_params
45
+ Peeky::Renderer::MethodCallMinimumParamsRender
46
+ else
47
+ raise "Unknown method renderer: #{key}"
48
+ end
49
+ end
50
+
51
+ # Get a class renderer by :key
52
+ #
53
+ # TODO: Refactor to a configurable system
54
+ def class_renderer(key)
55
+ case key
56
+ when :class_interface
57
+ Peeky::Renderer::ClassInterfaceRender
58
+ when :class_interface_yard
59
+ Peeky::Renderer::ClassInterfaceYardRender
60
+ else
61
+ raise "Unknown class renderer: #{key}"
62
+ end
63
+ end
64
+
65
+ # def render_method()
66
+ # end
67
+ end
68
+ end
69
+
70
+ Peeky.api = Peeky::Api.new
@@ -1,8 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Peeky
4
- # Class Info stores information about the
5
- # class instance that you pass in.
4
+ # Class Info stores information about the class instance that is provided.
6
5
  #
7
6
  # The information is collected into MethodInfo objects
8
7
  # that live within the signatures accessor.
@@ -10,6 +9,7 @@ module Peeky
10
9
  # This information is then separated out into
11
10
  # :methods, :attr_accessors, :attr_readers and :attr_writers
12
11
  class ClassInfo
12
+ # Holds an instance to the class you are gathering information from
13
13
  attr_reader :instance
14
14
 
15
15
  # Peak into class information
@@ -17,24 +17,106 @@ module Peeky
17
17
  @instance = instance
18
18
  end
19
19
 
20
- def class_name
20
+ # Class full name includes the module namespace
21
+ def class_full_name
21
22
  instance.class.name
22
23
  end
23
24
 
25
+ # Class name
26
+ def class_name
27
+ @_class_name ||= class_full_name.to_s.gsub(/^.*::/, '')
28
+ # instance.class.name.split('::').last
29
+ end
30
+
31
+ # Module name
32
+ def module_name
33
+ @_module_name ||= class_full_name.to_s.gsub(/(.*)::.*/, '\1')
34
+ end
35
+
36
+ # Get a list of :attr_accessor on the class
37
+ # @return [Array<AttrInfo>] list of AttrInfo where type is :attr_accessor
24
38
  def accessors
25
- @accessors ||= attribute_infos.select { |attribute_info| attribute_info.type == :attr_accessor }
39
+ @_accessors ||= attribute_infos.select { |attribute_info| attribute_info.type == :attr_accessor }
40
+ end
41
+
42
+ # Get a list of :attr_accessors ordered the way they are in the source code
43
+ # @return [Array<AttrInfo>] list of AttrInfo where type is :attr_accessor
44
+ def accessors_source_order
45
+ # TODO: This feature is required
46
+ # May be best to have a sort object that can be created for each type of ordering that is needed
47
+ accessors
48
+ end
49
+
50
+ # Attribute infos
51
+ def attribute_infos
52
+ @_attribute_infos ||= begin
53
+ grouped_method_infos = signatures.select { |signature| signature.readable? || signature.writable? }.group_by(&:clean_name)
54
+
55
+ grouped_method_infos.keys.map { |key| AttrInfo.create(*grouped_method_infos[key]) }
56
+ end
57
+ end
58
+
59
+ # Method by name
60
+ #
61
+ # @param name [String] name (required)
62
+ def method_by_name(name)
63
+ signatures_by_name(name, filter_type: :method).first
64
+ end
65
+
66
+ # Get a list methods
67
+ # @return [Array<MethodInfo>] list of MethodInfo where type is :method
68
+ def methods
69
+ @_methods ||= signatures.select { |signature| signature.implementation_type == :method }
70
+ end
71
+
72
+ # Get a list methods ordered the way they are in the source code
73
+ # @return [Array<MethodInfo>] list of MethodInfo
74
+ def methods_source_order
75
+ # TODO: This feature is required
76
+ # May be best to have a sort object that can be created for each type of ordering that is needed
77
+ methods
26
78
  end
27
79
 
80
+ # Reader by name
81
+ #
82
+ # @param name [String] name (required)
83
+ def reader_by_name(name)
84
+ signatures_by_name(name, filter_type: :attr_reader).first
85
+ end
86
+
87
+ # Get a list of :attr_reader on the class
88
+ # @return [Array<AttrInfo>] list of AttrInfo where type is :attr_accessor
28
89
  def readers
29
- @readers ||= attribute_infos.select { |attribute_info| attribute_info.type == :attr_reader }
90
+ @_readers ||= attribute_infos.select { |attribute_info| attribute_info.type == :attr_reader }
91
+ end
92
+
93
+ # Get a list of :attr_reader ordered the way they are in the source code
94
+ # @return [Array<AttrInfo>] list of AttrInfo where type is :attr_reader
95
+ def readers_source_order
96
+ # TODO: This feature is required
97
+ # May be best to have a sort object that can be created for each type of ordering that is needed
98
+ readers
30
99
  end
31
100
 
101
+ # Get a list of :attr_writer on the class
102
+ # @return [Array<AttrInfo>] list of AttrInfo where type is :attr_writer
32
103
  def writers
33
- @writers ||= attribute_infos.select { |attribute_info| attribute_info.type == :attr_writer }
104
+ @_writers ||= attribute_infos.select { |attribute_info| attribute_info.type == :attr_writer }
34
105
  end
35
106
 
36
- def methods
37
- @methods ||= signatures.select { |signature| signature.implementation_type == :method }
107
+ # Get a list of :attr_writer ordered the way they are in the source code
108
+ # @return [Array<AttrInfo>] list of AttrInfo where type is :attr_writer
109
+ def writers_source_order
110
+ # TODO: This feature is required
111
+ # May be best to have a sort object that can be created for each type of ordering that is needed
112
+ writers
113
+ end
114
+
115
+ # Writer by name
116
+ #
117
+ # @param name [String] name (required)
118
+ def writer_by_name(name)
119
+ signatures_by_name(name, filter_type: :attr_writer).first
38
120
  end
39
121
 
40
122
  # def signatures(types = [:instance])
@@ -42,36 +124,47 @@ module Peeky
42
124
  # such as static, private vs public
43
125
  # deep, deep_to_level, this_instance.
44
126
  def signatures
45
- @signatures ||= ruby_instance_methods.map { |im| MethodInfo.new(im, @instance) }
46
- end
47
-
48
- def signatures_by_name(name)
49
- signatures.select { |im| im.name == name }
127
+ @_signatures ||= ruby_instance_methods.map { |im| MethodInfo.new(im, @instance) }
50
128
  end
51
129
 
130
+ # Signatures by clean name
131
+ #
132
+ # @param clean_name [String] clean name (required)
52
133
  def signatures_by_clean_name(clean_name)
53
134
  signatures.select { |im| im.clean_name == clean_name }
54
135
  end
55
136
 
56
- def attribute_infos
57
- @attribute_infos ||= begin
58
- grouped_method_infos = signatures.select { |signature| signature.readable? || signature.writable? }.group_by(&:clean_name)
137
+ # Signatures by name
138
+ #
139
+ # @param name [String] name (required)
140
+ # @param filter_type [String] filter_type: <value for filter type> (optional)
141
+ def signatures_by_name(name, filter_type: :all)
142
+ return signatures.select { |im| im.name == name } if filter_type == :all
59
143
 
60
- grouped_method_infos.keys.map { |key| AttrInfo.create(*grouped_method_infos[key]) }
61
- end
144
+ signatures.select { |im| im.name == name && im.implementation_type == filter_type }
62
145
  end
63
146
 
147
+ # Build (not sure where I am going with this yet)
148
+ # TODO: Refact: Currently the idea is to pre-load data
149
+ # this is slower when you are not accessing things, but
150
+ # it is easier to debug, so think about what I really want
151
+ # here
152
+ def build
153
+ ruby_instance_methods
154
+ ruby_instance_method_names
155
+ signatures
156
+ end
157
+
158
+ # Debug
159
+ #
160
+ # Refact: PATTERN: Come up it an debug inclusion system so that
161
+ # so that debug helpers can be included for development and excluded
162
+ # for production
163
+ # @param format [String] format: <value for format> (optional)
64
164
  def debug(format: [:signatures])
65
- if format == :method_names
66
- puts '-' * 70
67
- puts 'Method Names'
68
- puts '-' * 70
69
- ruby_instance_method_names.each do |method_name|
70
- puts method_name
71
- end
72
- end
165
+ debug_method_names if format.include?(:method_names)
73
166
 
74
- return unless format == :signatures
167
+ return unless format.include?(:signatures)
75
168
 
76
169
  puts '-' * 70
77
170
  puts 'Methods'
@@ -79,14 +172,25 @@ module Peeky
79
172
  signatures.each(&:debug)
80
173
  end
81
174
 
175
+ def debug_method_names
176
+ puts '-' * 70
177
+ puts 'Method Names'
178
+ puts '-' * 70
179
+ ruby_instance_method_names.each do |method_name|
180
+ puts method_name
181
+ end
182
+ end
183
+
82
184
  private
83
185
 
84
186
  def ruby_instance_method_names
85
- @ruby_instance_method_names ||= instance.class.instance_methods(false).sort
187
+ @_ruby_instance_method_names ||= instance.class.instance_methods(false).sort
86
188
  end
87
189
 
88
190
  def ruby_instance_methods
89
- @ruby_instance_methods ||= ruby_instance_method_names.map { |method_name| instance.method(method_name) }
191
+ @_ruby_instance_methods ||= ruby_instance_method_names.map { |method_name| instance.method(method_name) }
192
+ rescue StandardError => e
193
+ puts e
90
194
  end
91
195
  end
92
196
  end