pry-stack_explorer 0.2.5pre1 → 0.2.6pre1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/Rakefile CHANGED
@@ -61,6 +61,12 @@ task :gems => [:clean, :rmgems, "ruby:gem"]
61
61
  desc "remove all platform gems"
62
62
  task :rmgems => ["ruby:clobber_package"]
63
63
 
64
+ desc "reinstall gem"
65
+ task :reinstall => :gems do
66
+ sh "gem uninstall pry-exception_explorer" rescue nil
67
+ sh "gem install #{direc}/pkg/#{PROJECT_NAME}-#{PryStackExplorer::VERSION}.gem"
68
+ end
69
+
64
70
  desc "build and push latest gems"
65
71
  task :pushgems => :gems do
66
72
  chdir("#{File.dirname(__FILE__)}/pkg") do
@@ -2,169 +2,52 @@
2
2
  # (C) John Mair (banisterfiend); MIT license
3
3
 
4
4
  require "pry-stack_explorer/version"
5
+ require "pry-stack_explorer/commands"
6
+ require "pry-stack_explorer/frame_manager"
5
7
  require "pry"
6
8
  require "binding_of_caller"
7
9
 
8
10
  module PryStackExplorer
11
+ Thread.current[:__pry_frame_managers__] ||= Hash.new { |h, k| h[k] = [] }
12
+
13
+ # Create a `Pry::FrameManager` object and push it onto the frame
14
+ # manager stack for the relevant `_pry_` instance.
15
+ # @param [Array] bindings The array of bindings (frames)
16
+ # @param [Pry] _pry_ The Pry instance associated with the frame manager
17
+ def self.push_and_create_frame_manager(bindings, _pry_)
18
+ Thread.current[:__pry_frame_managers__][_pry_].push FrameManager.new(bindings, _pry_)
19
+ end
9
20
 
10
- def self.add_frame_manager(bindings, _pry_)
11
- Thread.current[:__pry_frame_managers__] ||= {}
12
- Thread.current[:__pry_frame_managers__][_pry_] = FrameManager.new(bindings, _pry_)
21
+ # Delete the currently active frame manager
22
+ # @param [Pry] _pry_ The Pry instance associated with the frame managers
23
+ def self.pop_frame_manager(_pry_)
24
+ Thread.current[:__pry_frame_managers__][_pry_].pop
13
25
  end
14
26
 
15
- def self.delete_frame_manager(_pry_)
16
- Thread.current[:__pry_frame_managers__].delete(_pry_)
27
+ # Clear the stack of frame managers for the Pry instance
28
+ # @param [Pry] _pry_ The Pry instance associated with the frame managers
29
+ def self.clear_frame_managers(_pry_)
30
+ Thread.current[:__pry_frame_managers__][_pry_].clear
17
31
  end
18
32
 
33
+ # @return [PryStackExplorer::FrameManager] The currently active frame manager
19
34
  def self.frame_manager(_pry_)
20
- Thread.current[:__pry_frame_managers__][_pry_]
35
+ Thread.current[:__pry_frame_managers__][_pry_].last
21
36
  end
22
37
 
38
+ # Simple test to check whether two `Binding` objects are equal.
39
+ # @param [Binding] b1 First binding.
40
+ # @param [Binding] b2 Second binding.
23
41
  def self.bindings_equal?(b1, b2)
24
42
  (b1.eval('self') == b2.eval('self')) &&
25
43
  (b1.eval('__method__') == b2.eval('__method__')) &&
26
44
  (b1.eval('local_variables').map { |v| b1.eval("#{v}") } ==
27
45
  b2.eval('local_variables').map { |v| b2.eval("#{v}") })
28
46
  end
29
-
30
- class FrameManager
31
- attr_reader :binding_index
32
- attr_accessor :bindings
33
-
34
- def initialize(bindings, _pry_)
35
- @bindings = bindings
36
- @binding_index = 0
37
- @pry = _pry_
38
- end
39
-
40
- def convert_from_one_index(n)
41
- if n >= 0
42
- n - 1
43
- else
44
- n
45
- end
46
- end
47
- private :convert_from_one_index
48
-
49
- def signature(b)
50
- if b.eval('__method__')
51
- "#{closure_type} in #{b.eval('self').class}##{b.eval('__method__')}"
52
- else
53
- if b.eval('self').is_a?(Module)
54
- "#{closure_type} in <class:#{b.eval('self')}>"
55
- end
56
- end
57
- end
58
-
59
- def binding_info_for(b)
60
- b_self = b.eval('self')
61
- b_method = b.eval('__method__')
62
-
63
- if b_method && b_method != :__binding__ && b_method != :__binding_impl__
64
- b_method.to_s
65
- elsif b_self.instance_of?(Module)
66
- "<module:#{b_self}>"
67
- elsif b_self.instance_of?(Class)
68
- "<class:#{b_self}>"
69
- else
70
- "<main>"
71
- end
72
- end
73
-
74
- def change_binding_to(index)
75
- index = convert_from_one_index(index)
76
-
77
- if index > bindings.size - 1
78
- @pry.output.puts "Warning: At top of stack, cannot go further!"
79
- elsif index < 0
80
- @pry.output.puts "Warning: At bottom of stack, cannot go further!"
81
- else
82
- @binding_index = index
83
- @pry.binding_stack[-1] = bindings[binding_index]
84
-
85
- @pry.run_command "whereami"
86
- end
87
- end
88
- end
89
-
90
- StackCommands = Pry::CommandSet.new do
91
- command "up", "Go up to the caller's context" do |inc_str|
92
- inc = inc_str.nil? ? 1 : inc_str.to_i
93
-
94
- if !PryStackExplorer.frame_manager(_pry_)
95
- output.puts "Nowhere to go!"
96
- else
97
- binding_index = PryStackExplorer.frame_manager(_pry_).binding_index
98
- PryStackExplorer.frame_manager(_pry_).change_binding_to binding_index + inc + 1
99
- end
100
- end
101
-
102
- command "down", "Go down to the callee's context." do |inc_str|
103
- inc = inc_str.nil? ? 1 : inc_str.to_i
104
-
105
- if !PryStackExplorer.frame_manager(_pry_)
106
- output.puts "Nowhere to go!"
107
- else
108
- binding_index = PryStackExplorer.frame_manager(_pry_).binding_index
109
- PryStackExplorer.frame_manager(_pry_).change_binding_to binding_index - inc + 1
110
- end
111
- end
112
-
113
- command "show-stack", "Show all frames" do |*args|
114
- opts = parse_options!(args) do |opt|
115
- opt.banner unindent <<-USAGE
116
- Usage: show-stack [OPTIONS]
117
- Show all accessible stack frames.
118
- e.g: show-stack -v
119
- USAGE
120
-
121
- opt.on :v, :verbose, "Include extra information."
122
- end
123
-
124
- if !PryStackExplorer.frame_manager(_pry_)
125
- output.puts "No caller stack available!"
126
- else
127
- output.puts "\n#{text.bold('Showing all accessible frames in stack:')}\n--\n"
128
-
129
- PryStackExplorer.frame_manager(_pry_).bindings.each_with_index do |b, i|
130
- meth = b.eval('__method__')
131
- b_self = b.eval('self')
132
-
133
- desc = b.frame_description ? "#{text.bold('Description:')} #{b.frame_description}".ljust(40) :
134
- "#{text.bold('Description:')} #{PryStackExplorer.frame_manager(_pry_).binding_info_for(b)}".ljust(40)
135
- sig = meth ? "#{text.bold('Signature:')} #{Pry::Method.new(b_self.method(meth)).signature}".ljust(40) : "".ljust(32)
136
- type = b.frame_type ? "#{text.bold('Type:')} #{b.frame_type}".ljust(20) : "".ljust(20)
137
- slf = "#{text.bold('Self:')} #{b_self}".ljust(20)
138
- path = "#{text.bold("@ File:")} #{b.eval('__FILE__')}:#{b.eval('__LINE__')}"
139
-
140
- info = "##{i + 1} #{desc} #{sig} #{slf if opts[:v]} #{type \
141
- if opts[:v]} #{path if opts[:v]}"
142
- if i == PryStackExplorer.frame_manager(_pry_).binding_index
143
-
144
- output.puts "=> #{info}"
145
- else
146
- output.puts " #{info}"
147
- end
148
- end
149
- end
150
- end
151
-
152
- command "frame", "Switch to a particular frame." do |frame_num|
153
- if !PryStackExplorer.frame_manager(_pry_)
154
- output.puts "nowhere to go!"
155
- else
156
- PryStackExplorer.frame_manager(_pry_).change_binding_to frame_num.to_i
157
- end
158
- end
159
-
160
- command "frame-type", "Display current frame type." do
161
- output.puts _pry_.binding_stack.last.frame_type
162
- end
163
- end
164
47
  end
165
48
 
166
49
  Pry.config.hooks.add_hook(:after_session, :delete_frame_manager) do |_, _, _pry_|
167
- PryStackExplorer.delete_frame_manager(_pry_)
50
+ PryStackExplorer.clear_frame_managers(_pry_)
168
51
  end
169
52
 
170
53
  Pry.config.hooks.add_hook(:when_started, :save_caller_bindings) do |binding_stack, _pry_|
@@ -187,9 +70,10 @@ Pry.config.hooks.add_hook(:when_started, :save_caller_bindings) do |binding_stac
187
70
  end
188
71
 
189
72
  binding_stack.replace([bindings.first])
190
- PryStackExplorer.add_frame_manager(bindings, _pry_)
73
+ PryStackExplorer.push_and_create_frame_manager(bindings, _pry_)
191
74
  end
192
75
 
76
+ # Import the StackExplorer commands
193
77
  Pry.config.commands.import PryStackExplorer::StackCommands
194
78
 
195
79
  # monkey-patch the whereami command to show some frame information,
@@ -200,7 +84,7 @@ Pry.config.commands.before_command("whereami") do |num|
200
84
  binding_index = PryStackExplorer.frame_manager(_pry_).binding_index
201
85
 
202
86
  output.puts "\n"
203
- output.puts "#{Pry::Helpers::Text.bold('Frame number:')} #{binding_index + 1}/#{bindings.size}"
87
+ output.puts "#{Pry::Helpers::Text.bold('Frame number:')} #{binding_index}/#{bindings.size - 1}"
204
88
  output.puts "#{Pry::Helpers::Text.bold('Frame type:')} #{bindings[binding_index].frame_type}" if bindings[binding_index].frame_type
205
89
  end
206
90
  end
@@ -0,0 +1,75 @@
1
+ module PryStackExplorer
2
+ StackCommands = Pry::CommandSet.new do
3
+ command "up", "Go up to the caller's context" do |inc_str|
4
+ inc = inc_str.nil? ? 1 : inc_str.to_i
5
+
6
+ if !PryStackExplorer.frame_manager(_pry_)
7
+ output.puts "Nowhere to go!"
8
+ else
9
+ binding_index = PryStackExplorer.frame_manager(_pry_).binding_index
10
+ PryStackExplorer.frame_manager(_pry_).change_frame_to binding_index + inc
11
+ end
12
+ end
13
+
14
+ command "down", "Go down to the callee's context." do |inc_str|
15
+ inc = inc_str.nil? ? 1 : inc_str.to_i
16
+
17
+ if !PryStackExplorer.frame_manager(_pry_)
18
+ output.puts "Nowhere to go!"
19
+ else
20
+ binding_index = PryStackExplorer.frame_manager(_pry_).binding_index
21
+ PryStackExplorer.frame_manager(_pry_).change_frame_to binding_index - inc
22
+ end
23
+ end
24
+
25
+ command "show-stack", "Show all frames" do |*args|
26
+ opts = parse_options!(args) do |opt|
27
+ opt.banner unindent <<-USAGE
28
+ Usage: show-stack [OPTIONS]
29
+ Show all accessible stack frames.
30
+ e.g: show-stack -v
31
+ USAGE
32
+
33
+ opt.on :v, :verbose, "Include extra information."
34
+ end
35
+
36
+ if !PryStackExplorer.frame_manager(_pry_)
37
+ output.puts "No caller stack available!"
38
+ else
39
+ output.puts "\n#{text.bold('Showing all accessible frames in stack:')}\n--\n"
40
+
41
+ PryStackExplorer.frame_manager(_pry_).each_with_index do |b, i|
42
+ meth = b.eval('__method__')
43
+ b_self = b.eval('self')
44
+
45
+ desc = b.frame_description ? "#{text.bold('Description:')} #{b.frame_description}".ljust(40) :
46
+ "#{text.bold('Description:')} #{PryStackExplorer.frame_manager(_pry_).frame_info_for(b)}".ljust(40)
47
+ sig = meth ? "#{text.bold('Signature:')} #{Pry::Method.new(b_self.method(meth)).signature}".ljust(40) : "".ljust(32)
48
+ type = b.frame_type ? "#{text.bold('Type:')} #{b.frame_type}".ljust(20) : "".ljust(20)
49
+ slf_class = "#{text.bold('Self.class:')} #{b_self.class}".ljust(20)
50
+ path = "#{text.bold("@ File:")} #{b.eval('__FILE__')}:#{b.eval('__LINE__')}"
51
+
52
+ info = "##{i} #{desc} #{slf_class} #{sig} #{type \
53
+ if opts[:v]} #{path if opts[:v]}"
54
+ if i == PryStackExplorer.frame_manager(_pry_).binding_index
55
+ output.puts "=> #{info}"
56
+ else
57
+ output.puts " #{info}"
58
+ end
59
+ end
60
+ end
61
+ end
62
+
63
+ command "frame", "Switch to a particular frame." do |frame_num|
64
+ if !PryStackExplorer.frame_manager(_pry_)
65
+ output.puts "nowhere to go!"
66
+ else
67
+ PryStackExplorer.frame_manager(_pry_).change_frame_to frame_num.to_i
68
+ end
69
+ end
70
+
71
+ command "frame-type", "Display current frame type." do
72
+ output.puts _pry_.binding_stack.last.frame_type
73
+ end
74
+ end
75
+ end
@@ -0,0 +1,80 @@
1
+ module PryStackExplorer
2
+
3
+ class FrameManager
4
+ include Enumerable
5
+
6
+ attr_accessor :binding_index
7
+ attr_accessor :bindings
8
+
9
+ # @return [Hash] A hash for user defined data
10
+ attr_reader :user
11
+
12
+ def initialize(bindings, _pry_)
13
+ self.bindings = bindings
14
+ self.binding_index = 0
15
+ @pry = _pry_
16
+ @user = {}
17
+ end
18
+
19
+ # Replace the current set of bindings (call stack) and binding
20
+ # index (current frame)
21
+ # @param [Array] bindings The new call stack (array of bindings)
22
+ # @param [Fixnum] binding_index The currently 'active' frame (binding).
23
+ def replace_call_stack(bindings, binding_index = 0)
24
+ self.bindings = bindings
25
+ self.binding_index = binding_index
26
+ end
27
+
28
+ # Iterate over all frames
29
+ def each(&block)
30
+ bindings.each(&block)
31
+ end
32
+
33
+ # Return a description of the frame (binding)
34
+ # @param [Binding] b The binding.
35
+ # @return [String] A description of the frame (binding).
36
+ def frame_info_for(b)
37
+ b_self = b.eval('self')
38
+ b_method = b.eval('__method__')
39
+
40
+ if b_method && b_method != :__binding__ && b_method != :__binding_impl__
41
+ b_method.to_s
42
+ elsif b_self.instance_of?(Module)
43
+ "<module:#{b_self}>"
44
+ elsif b_self.instance_of?(Class)
45
+ "<class:#{b_self}>"
46
+ else
47
+ "<main>"
48
+ end
49
+ end
50
+
51
+ # Ensure the Pry instance's active binding is the frame manager's
52
+ # active binding.
53
+ def refresh_frame
54
+ change_frame_to binding_index
55
+ end
56
+
57
+ # @return [Binding] The currently active frame
58
+ def current_frame
59
+ bindings[binding_index]
60
+ end
61
+
62
+ # Change active frame to the one indexed by `index`.
63
+ # Note that indexing base is `0`
64
+ # @param [Fixnum] index The index of the frame.
65
+ def change_frame_to(index)
66
+
67
+ if index > bindings.size - 1
68
+ @pry.output.puts "Warning: At top of stack, cannot go further!"
69
+ elsif index < 0
70
+ @pry.output.puts "Warning: At bottom of stack, cannot go further!"
71
+ else
72
+ self.binding_index = index
73
+ @pry.binding_stack[-1] = bindings[binding_index]
74
+
75
+ @pry.run_command "whereami"
76
+ end
77
+ end
78
+
79
+ end
80
+ end
@@ -1,3 +1,3 @@
1
1
  module PryStackExplorer
2
- VERSION = "0.2.5pre1"
2
+ VERSION = "0.2.6pre1"
3
3
  end
metadata CHANGED
@@ -2,7 +2,7 @@
2
2
  name: pry-stack_explorer
3
3
  version: !ruby/object:Gem::Version
4
4
  prerelease: 5
5
- version: 0.2.5pre1
5
+ version: 0.2.6pre1
6
6
  platform: ruby
7
7
  authors:
8
8
  - John Mair (banisterfiend)
@@ -10,7 +10,7 @@ autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
12
 
13
- date: 2011-12-06 00:00:00 Z
13
+ date: 2011-12-15 00:00:00 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: binding_of_caller
@@ -43,6 +43,8 @@ extensions: []
43
43
  extra_rdoc_files: []
44
44
 
45
45
  files:
46
+ - lib/pry-stack_explorer/commands.rb
47
+ - lib/pry-stack_explorer/frame_manager.rb
46
48
  - lib/pry-stack_explorer/version.rb
47
49
  - lib/pry-stack_explorer.rb
48
50
  - test/test.rb