byebug 1.5.0 → 1.6.0
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.
- checksums.yaml +4 -4
- data/.gitignore +2 -0
- data/.travis.yml +0 -1
- data/CHANGELOG.md +8 -0
- data/GUIDE.md +52 -32
- data/README.md +6 -0
- data/ext/byebug/byebug.c +19 -3
- data/ext/byebug/byebug.h +4 -3
- data/ext/byebug/context.c +21 -5
- data/lib/byebug.rb +5 -14
- data/lib/byebug/command.rb +1 -1
- data/lib/byebug/commands/frame.rb +28 -44
- data/lib/byebug/commands/info.rb +2 -1
- data/lib/byebug/commands/list.rb +1 -1
- data/lib/byebug/commands/repl.rb +7 -21
- data/lib/byebug/commands/set.rb +4 -9
- data/lib/byebug/commands/trace.rb +2 -2
- data/lib/byebug/context.rb +7 -16
- data/lib/byebug/processor.rb +16 -18
- data/lib/byebug/version.rb +1 -1
- data/old_doc/byebug.texi +12 -17
- data/test/breakpoints_test.rb +75 -61
- data/test/conditions_test.rb +7 -7
- data/test/continue_test.rb +5 -5
- data/test/display_test.rb +6 -6
- data/test/edit_test.rb +2 -2
- data/test/examples/{breakpoint1.rb → breakpoint.rb} +0 -0
- data/test/examples/breakpoint_deep.rb +24 -0
- data/test/finish_test.rb +5 -5
- data/test/frame_test.rb +27 -38
- data/test/jump_test.rb +6 -7
- data/test/list_test.rb +1 -1
- data/test/post_mortem_test.rb +1 -1
- data/test/repl_test.rb +4 -40
- data/test/set_test.rb +3 -3
- data/test/show_test.rb +1 -1
- data/test/stepping_test.rb +15 -16
- data/test/support/test_dsl.rb +9 -16
- data/test/trace_test.rb +2 -2
- metadata +6 -6
- data/test/support/mocha_extensions.rb +0 -71
@@ -16,12 +16,9 @@ module Byebug
|
|
16
16
|
end
|
17
17
|
|
18
18
|
if abs_frame_pos >= context.stack_size then
|
19
|
-
return
|
20
|
-
errmsg "Adjusting would put us beyond the oldest (initial) frame.\n"
|
19
|
+
return errmsg "Adjusting would put us beyond the oldest frame.\n"
|
21
20
|
elsif abs_frame_pos < 0 then
|
22
|
-
return
|
23
|
-
errmsg "Adjusting would put us beyond the newest (innermost) frame.\n"
|
24
|
-
return
|
21
|
+
return errmsg "Adjusting would put us beyond the newest frame.\n"
|
25
22
|
end
|
26
23
|
|
27
24
|
if @state.frame_pos != abs_frame_pos then
|
@@ -35,48 +32,36 @@ module Byebug
|
|
35
32
|
print_frame @state.frame_pos, false
|
36
33
|
end
|
37
34
|
|
38
|
-
def
|
39
|
-
|
40
|
-
return "
|
41
|
-
|
42
|
-
klass = @state.context.frame_class(pos)
|
35
|
+
def get_frame_class(style, pos)
|
36
|
+
frame_class = style == :short ? '' : "#{@state.context.frame_class pos}"
|
37
|
+
return frame_class == '' ? '' : "#{frame_class}."
|
38
|
+
end
|
43
39
|
|
44
|
-
|
45
|
-
|
40
|
+
def get_frame_args(style, pos)
|
41
|
+
args = @state.context.frame_args pos
|
42
|
+
if args == [[:rest]]
|
43
|
+
frame_args = ''
|
44
|
+
elsif style == :short
|
45
|
+
frame_args = args.map { |_, name| name }.join(', ')
|
46
46
|
else
|
47
|
-
|
47
|
+
locals = @state.context.frame_locals pos
|
48
|
+
frame_args = args.map { |_, a| "#{a}##{locals[a].class}" }.join(', ')
|
48
49
|
end
|
50
|
+
return frame_args == '' ? '' : "(#{frame_args})"
|
51
|
+
end
|
49
52
|
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
if klass.inspect.size > 20 + 3
|
61
|
-
klass = klass.inspect[0..20] + "..."
|
62
|
-
end
|
63
|
-
call_str += "#{name}##{klass}, "
|
64
|
-
when :tracked
|
65
|
-
arg_info = context.frame_args_info pos
|
66
|
-
if arg_info && arg_info.size > i
|
67
|
-
call_str += "#{name}: #{arg_info[i].inspect}, "
|
68
|
-
else
|
69
|
-
call_str += "#{name}, "
|
70
|
-
end
|
71
|
-
end
|
72
|
-
if call_str.size > Command.settings[:width] - prefix.size
|
73
|
-
# Strip off trailing ', ' if any but add stuff for later trunc
|
74
|
-
call_str[-2..-1] = ",...XX"
|
75
|
-
break
|
76
|
-
end
|
77
|
-
end
|
78
|
-
call_str[-2..-1] = ")" # Strip off trailing ', ' if any
|
53
|
+
def get_frame_call(prefix, pos)
|
54
|
+
frame_class = get_frame_class(Command.settings[:callstyle], pos)
|
55
|
+
frame_method = "#{@state.context.frame_method pos}"
|
56
|
+
frame_args = get_frame_args(Command.settings[:callstyle], pos)
|
57
|
+
|
58
|
+
call_str = frame_class + frame_method + frame_args
|
59
|
+
|
60
|
+
max_call_str_size = Command.settings[:width] - prefix.size
|
61
|
+
if call_str.size > max_call_str_size
|
62
|
+
call_str = call_str[0..max_call_str_size - 5] + "...)"
|
79
63
|
end
|
64
|
+
|
80
65
|
return call_str
|
81
66
|
end
|
82
67
|
|
@@ -199,8 +184,7 @@ module Byebug
|
|
199
184
|
if not @match[1]
|
200
185
|
pos = 0
|
201
186
|
else
|
202
|
-
pos = get_int(@match[1], "Frame")
|
203
|
-
return unless pos
|
187
|
+
return unless pos = get_int(@match[1], "Frame")
|
204
188
|
end
|
205
189
|
adjust_frame(pos, true)
|
206
190
|
end
|
data/lib/byebug/commands/info.rb
CHANGED
@@ -84,8 +84,9 @@ module Byebug
|
|
84
84
|
|
85
85
|
locals = @state.context.frame_locals
|
86
86
|
args = @state.context.frame_args
|
87
|
+
return if args == [[:rest]]
|
87
88
|
|
88
|
-
args.
|
89
|
+
args.map do |_, name|
|
89
90
|
s = "#{name} = #{locals[name].inspect}"
|
90
91
|
pad_with_dots(s)
|
91
92
|
print "#{s}\n"
|
data/lib/byebug/commands/list.rb
CHANGED
@@ -21,7 +21,7 @@ module Byebug
|
|
21
21
|
Byebug.source_reload if Command.settings[:autoreload]
|
22
22
|
lines = LineCache::getlines @state.file, Command.settings[:autoreload]
|
23
23
|
if !lines
|
24
|
-
errmsg "No sourcefile available for #{@state.file}\n"
|
24
|
+
errmsg "No sourcefile available for #{@state.file}\n"
|
25
25
|
return @state.previous_line
|
26
26
|
end
|
27
27
|
|
data/lib/byebug/commands/repl.rb
CHANGED
@@ -60,9 +60,7 @@ module Byebug
|
|
60
60
|
end
|
61
61
|
|
62
62
|
def regexp
|
63
|
-
/^\s* irb
|
64
|
-
(?:\s+(-d))?
|
65
|
-
\s*$/x
|
63
|
+
/^\s* irb \s*$/x
|
66
64
|
end
|
67
65
|
|
68
66
|
def execute
|
@@ -71,9 +69,6 @@ module Byebug
|
|
71
69
|
throw :debug_error
|
72
70
|
end
|
73
71
|
|
74
|
-
add_debugging = @match.is_a?(MatchData) && '-d' == @match[1]
|
75
|
-
$byebug_state = @state if add_debugging
|
76
|
-
|
77
72
|
cont = IRB.start_session(get_binding)
|
78
73
|
case cont
|
79
74
|
when :cont
|
@@ -92,7 +87,6 @@ module Byebug
|
|
92
87
|
CommandProcessor.print_location_and_text(file, line)
|
93
88
|
@state.previous_line = nil
|
94
89
|
end
|
95
|
-
$byebug_state = nil if add_debugging
|
96
90
|
end
|
97
91
|
|
98
92
|
|
@@ -102,12 +96,11 @@ module Byebug
|
|
102
96
|
end
|
103
97
|
|
104
98
|
def description
|
105
|
-
%{irb
|
99
|
+
%{irb\tstarts an Interactive Ruby (IRB) session.
|
106
100
|
|
107
|
-
|
108
|
-
|
109
|
-
|
110
|
-
real byebug commands these commands don't allow arguments.}
|
101
|
+
IRB is extended with methods "cont", "n" and "step" which run the
|
102
|
+
corresponding byebug commands. In contrast to the real byebug commands
|
103
|
+
these commands don't allow arguments.}
|
111
104
|
end
|
112
105
|
end
|
113
106
|
end
|
@@ -122,9 +115,7 @@ module Byebug
|
|
122
115
|
# Implements byebug's "pry" command
|
123
116
|
class PryCommand < Command
|
124
117
|
def regexp
|
125
|
-
/^\s* pry
|
126
|
-
(?:\s+(-d))?
|
127
|
-
\s*$/x
|
118
|
+
/^\s* pry \s*$/x
|
128
119
|
end
|
129
120
|
|
130
121
|
def execute
|
@@ -133,12 +124,7 @@ module Byebug
|
|
133
124
|
throw :debug_error
|
134
125
|
end
|
135
126
|
|
136
|
-
add_debugging = @match.is_a?(MatchData) && '-d' == @match[1]
|
137
|
-
$byebug_state = @state if add_debugging
|
138
|
-
|
139
127
|
get_binding.pry
|
140
|
-
|
141
|
-
$byebug_state = nil if add_debugging
|
142
128
|
end
|
143
129
|
|
144
130
|
class << self
|
@@ -147,7 +133,7 @@ module Byebug
|
|
147
133
|
end
|
148
134
|
|
149
135
|
def description
|
150
|
-
%{pry
|
136
|
+
%{pry\tstarts a Pry session.}
|
151
137
|
end
|
152
138
|
end
|
153
139
|
end if has_pry
|
data/lib/byebug/commands/set.rb
CHANGED
@@ -94,15 +94,10 @@ module Byebug
|
|
94
94
|
when /^basename$/
|
95
95
|
Command.settings[:basename] = set_on
|
96
96
|
when /^callstyle$/
|
97
|
-
if args[0]
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
Command.settings[:callstyle] = arg
|
102
|
-
else
|
103
|
-
print "Invalid call style #{arg}. Should be one of: " \
|
104
|
-
"\"short\", \"last\" or \"tracked\".\n"
|
105
|
-
end
|
97
|
+
if args[0] and (args[0] == 'short' or arg[0] == 'long')
|
98
|
+
Command.settings[:callstyle] = arg[0].to_sym
|
99
|
+
else
|
100
|
+
print "Invalid callstyle. Should be one of: \"short\" or \"long\"\n"
|
106
101
|
end
|
107
102
|
when /^trace$/
|
108
103
|
Command.settings[:stack_trace_on_error] = set_on
|
@@ -14,12 +14,12 @@ module Byebug
|
|
14
14
|
Byebug.tracing = onoff
|
15
15
|
print "#{show_setting('linetrace')}\n"
|
16
16
|
elsif @match[1] =~ /var(?:iable)?/
|
17
|
-
varname
|
17
|
+
varname = @match[2]
|
18
18
|
if debug_eval("defined?(#{varname})")
|
19
19
|
if @match[3] && @match[3] !~ /(:?no)?stop/
|
20
20
|
errmsg "expecting \"stop\" or \"nostop\"; got \"#{@match[3]}\"\n"
|
21
21
|
else
|
22
|
-
dbg_cmd = (@match[3] &&
|
22
|
+
dbg_cmd = (@match[3] && @match[3] !~ /nostop/) ? 'byebug(1,0)' : ''
|
23
23
|
end
|
24
24
|
eval("trace_var(:#{varname}) do |val|
|
25
25
|
print \"traced variable \#{varname} has value \#{val}\n\"
|
data/lib/byebug/context.rb
CHANGED
@@ -8,24 +8,12 @@ module Byebug
|
|
8
8
|
end
|
9
9
|
|
10
10
|
class Context
|
11
|
-
def frame_args frame_no = 0
|
12
|
-
bind = frame_binding frame_no
|
13
|
-
return [] unless eval "__method__", bind
|
14
|
-
begin
|
15
|
-
eval "self.method(__method__).parameters.map{|(attr, mid)| mid}", bind
|
16
|
-
rescue NameError => e
|
17
|
-
print "(WARNING: retreving args from frame #{frame_no} => " \
|
18
|
-
"#{e.class} Exception: #{e.message})\n "
|
19
|
-
return []
|
20
|
-
end
|
21
|
-
end
|
22
|
-
|
23
11
|
def frame_locals frame_no = 0
|
24
12
|
bind = frame_binding frame_no
|
25
13
|
eval "local_variables.inject({}){|h, v| h[v] = eval(v.to_s); h}", bind
|
26
14
|
end
|
27
15
|
|
28
|
-
def
|
16
|
+
def frame_args frame_no = 0
|
29
17
|
bind = frame_binding frame_no
|
30
18
|
return [] unless eval "__method__", bind
|
31
19
|
eval "self.method(__method__).parameters", bind
|
@@ -35,9 +23,8 @@ module Byebug
|
|
35
23
|
Byebug.handler or raise 'No interface loaded'
|
36
24
|
end
|
37
25
|
|
38
|
-
def at_breakpoint(
|
39
|
-
handler.at_breakpoint(self,
|
40
|
-
IGNORED_FILES.include?(breakpoint.source)
|
26
|
+
def at_breakpoint(brkpnt)
|
27
|
+
handler.at_breakpoint(self, brkpnt)
|
41
28
|
end
|
42
29
|
|
43
30
|
def at_catchpoint(excpt)
|
@@ -51,5 +38,9 @@ module Byebug
|
|
51
38
|
def at_line(file, line)
|
52
39
|
handler.at_line(self, file, line) unless IGNORED_FILES.include?(file)
|
53
40
|
end
|
41
|
+
|
42
|
+
def at_return(file, line)
|
43
|
+
handler.at_return(self, file, line) unless IGNORED_FILES.include?(file)
|
44
|
+
end
|
54
45
|
end
|
55
46
|
end
|
data/lib/byebug/processor.rb
CHANGED
@@ -82,7 +82,7 @@ module Byebug
|
|
82
82
|
end
|
83
83
|
|
84
84
|
def self.print_location_and_text(file, line)
|
85
|
-
if file == '(irb)'
|
85
|
+
if file == '(irb)' || file == '-e'
|
86
86
|
file_line = "#{canonic_file(file)} @ #{line}\n"
|
87
87
|
else
|
88
88
|
file_line = "#{canonic_file(file)} @ #{line}\n" \
|
@@ -159,6 +159,11 @@ module Byebug
|
|
159
159
|
end
|
160
160
|
protect :at_line
|
161
161
|
|
162
|
+
def at_return(context, file, line)
|
163
|
+
process_commands(context, file, line)
|
164
|
+
end
|
165
|
+
protect :at_return
|
166
|
+
|
162
167
|
private
|
163
168
|
##
|
164
169
|
# Prompt shown before reading a command.
|
@@ -185,15 +190,10 @@ module Byebug
|
|
185
190
|
cmd.allow_in_post_mortem
|
186
191
|
end if context.dead?
|
187
192
|
|
188
|
-
state = State.new
|
189
|
-
|
190
|
-
|
191
|
-
|
192
|
-
s.display = display
|
193
|
-
s.interface = interface
|
194
|
-
s.commands = event_cmds
|
195
|
-
end
|
196
|
-
@interface.state = state if @interface.respond_to?('state=')
|
193
|
+
state = State.new(event_cmds, context, display, file, interface, line)
|
194
|
+
|
195
|
+
# Change default when in irb or code included in command line
|
196
|
+
Command.settings[:autolist] = 0 if file == '(irb)' or file == '-e'
|
197
197
|
|
198
198
|
# Bind commands to the current state.
|
199
199
|
commands = event_cmds.map{|cmd| cmd.new(state)}
|
@@ -209,7 +209,7 @@ module Byebug
|
|
209
209
|
#
|
210
210
|
def process_commands(context, file, line)
|
211
211
|
state, commands = always_run(context, file, line, 1)
|
212
|
-
$
|
212
|
+
$state = Command.settings[:testing] ? state : nil
|
213
213
|
|
214
214
|
splitter = lambda do |str|
|
215
215
|
str.split(/;/).inject([]) do |m, v|
|
@@ -229,7 +229,7 @@ module Byebug
|
|
229
229
|
|
230
230
|
preloop(commands, context)
|
231
231
|
|
232
|
-
if Command.settings[:autolist] == 0
|
232
|
+
if Command.settings[:autolist] == 0
|
233
233
|
CommandProcessor.print_location_and_text(file, line)
|
234
234
|
end
|
235
235
|
|
@@ -338,12 +338,10 @@ module Byebug
|
|
338
338
|
attr_accessor :commands, :context, :display, :file
|
339
339
|
attr_accessor :frame_pos, :interface, :line, :previous_line
|
340
340
|
|
341
|
-
def initialize
|
342
|
-
|
343
|
-
@
|
344
|
-
@previous_line = nil
|
345
|
-
@proceed = false
|
346
|
-
yield self
|
341
|
+
def initialize(commands, context, display, file, interface, line)
|
342
|
+
@commands, @context, @display = commands, context, display
|
343
|
+
@file, @interface, @line = file, interface, line
|
344
|
+
@frame_pos, @previous_line, @proceed = 0, nil, false
|
347
345
|
end
|
348
346
|
|
349
347
|
extend Forwardable
|
data/lib/byebug/version.rb
CHANGED
data/old_doc/byebug.texi
CHANGED
@@ -2519,24 +2519,19 @@ Shows the whether filename display shows just the file basename or not.
|
|
2519
2519
|
|
2520
2520
|
@table @code
|
2521
2521
|
@ifset FINISHED
|
2522
|
-
@kindex set callstyle @r{[} short |
|
2523
|
-
@item set
|
2522
|
+
@kindex set callstyle @r{[} short | long @r{]}
|
2523
|
+
@item set callstyle @r{[} short | long @r{]}
|
2524
2524
|
@else
|
2525
|
-
@kindex set callstyle @r{[} short |
|
2526
|
-
@item set
|
2525
|
+
@kindex set callstyle @r{[} short | long
|
2526
|
+
@item set callstyle @r{[} short | long
|
2527
2527
|
@end ifset
|
2528
2528
|
|
2529
|
-
Sets how you want call parameters displayed
|
2530
|
-
|
2531
|
-
@
|
2532
|
-
@code{
|
2533
|
-
|
2534
|
-
|
2535
|
-
values.
|
2536
|
-
@end ifset
|
2537
|
-
@code{tracked} is the most accurate but this adds
|
2538
|
-
overhead. On every call, scalar values of the parameters get
|
2539
|
-
saved. For non-scalar values the class is saved.
|
2529
|
+
Sets how you want call parameters displayed
|
2530
|
+
|
2531
|
+
@code{short} shows current method and parameter names.
|
2532
|
+
@code{long} shows current class, current method, parameter names and the class
|
2533
|
+
of each parameter as it currently exist. Note the type could have changed
|
2534
|
+
since the call was made.
|
2540
2535
|
@end table
|
2541
2536
|
|
2542
2537
|
@node Forcestep
|
@@ -2965,7 +2960,7 @@ Fixnum: 1 if on or 0 if off.
|
|
2965
2960
|
@item :basename
|
2966
2961
|
Boolean. True if basename on. @xref{Basename}.
|
2967
2962
|
@item :callstyle
|
2968
|
-
Symbol: @code{:short} or @code{:
|
2963
|
+
Symbol: @code{:short} or @code{:long}. @xref{Callstyle}.
|
2969
2964
|
@item :testing
|
2970
2965
|
Boolean. True if currently testing byebug.
|
2971
2966
|
@item :force_stepping
|
@@ -3226,7 +3221,7 @@ y = 1
|
|
3226
3221
|
|
3227
3222
|
$ ruby scope-test.rb
|
3228
3223
|
../lib/byebug.rb:386
|
3229
|
-
Byebug.context.
|
3224
|
+
Byebug.context.after_frame = 0
|
3230
3225
|
(byebug:1) where
|
3231
3226
|
--> #0 Kernel.byebug(steps#Fixnum) at ../lib/byebug-base.rb:386
|
3232
3227
|
#1 at scope-test.rb:4
|
data/test/breakpoints_test.rb
CHANGED
@@ -7,28 +7,28 @@ class TestBreakpoints < TestDsl::TestCase
|
|
7
7
|
subject { Byebug.breakpoints.first }
|
8
8
|
|
9
9
|
def check_subject(field, value)
|
10
|
-
debug_file('
|
10
|
+
debug_file('breakpoint') { subject.send(field).must_equal value }
|
11
11
|
end
|
12
12
|
|
13
13
|
it('must have correct pos') { check_subject(:pos, 10) }
|
14
14
|
it('must have correct source') {
|
15
|
-
check_subject(:source, fullpath('
|
15
|
+
check_subject(:source, fullpath('breakpoint')) }
|
16
16
|
it('must have correct expression') { check_subject(:expr, nil) }
|
17
17
|
it('must have correct hit count') { check_subject(:hit_count, 0) }
|
18
18
|
it('must have correct hit value') { check_subject(:hit_value, 0) }
|
19
19
|
it('must be enabled') { check_subject(:enabled?, true) }
|
20
20
|
it('must return right response') do
|
21
21
|
id = nil
|
22
|
-
debug_file('
|
22
|
+
debug_file('breakpoint') { id = subject.id }
|
23
23
|
check_output_includes \
|
24
|
-
"Created breakpoint #{id} at #{fullpath('
|
24
|
+
"Created breakpoint #{id} at #{fullpath('breakpoint')}:10"
|
25
25
|
end
|
26
26
|
end
|
27
27
|
|
28
28
|
describe 'using shortcut for the command' do
|
29
29
|
before { enter 'b 10' }
|
30
30
|
it 'must set a breakpoint' do
|
31
|
-
debug_file('
|
31
|
+
debug_file('breakpoint') { Byebug.breakpoints.size.must_equal 1 }
|
32
32
|
end
|
33
33
|
end
|
34
34
|
|
@@ -36,14 +36,14 @@ class TestBreakpoints < TestDsl::TestCase
|
|
36
36
|
before { enter 'break 100' }
|
37
37
|
|
38
38
|
it 'must not create a breakpoint' do
|
39
|
-
debug_file('
|
39
|
+
debug_file('breakpoint') { Byebug.breakpoints.must_be_empty }
|
40
40
|
end
|
41
41
|
|
42
42
|
it 'must show an error' do
|
43
|
-
debug_file('
|
43
|
+
debug_file('breakpoint')
|
44
44
|
check_output_includes \
|
45
|
-
"There are only #{LineCache.size(fullpath('
|
46
|
-
" file #{fullpath('
|
45
|
+
"There are only #{LineCache.size(fullpath('breakpoint'))} lines in" \
|
46
|
+
" file #{fullpath('breakpoint')}", interface.error_queue
|
47
47
|
end
|
48
48
|
end
|
49
49
|
|
@@ -52,13 +52,13 @@ class TestBreakpoints < TestDsl::TestCase
|
|
52
52
|
before { enter 'break 11' }
|
53
53
|
|
54
54
|
it 'must not create a breakpoint' do
|
55
|
-
debug_file('
|
55
|
+
debug_file('breakpoint') { Byebug.breakpoints.must_be_empty }
|
56
56
|
end
|
57
57
|
|
58
58
|
it 'must show an error' do
|
59
|
-
debug_file('
|
59
|
+
debug_file('breakpoint')
|
60
60
|
check_output_includes \
|
61
|
-
"Line 11 is not a stopping point in file #{fullpath('
|
61
|
+
"Line 11 is not a stopping point in file #{fullpath('breakpoint')}",
|
62
62
|
interface.error_queue
|
63
63
|
end
|
64
64
|
end
|
@@ -66,13 +66,13 @@ class TestBreakpoints < TestDsl::TestCase
|
|
66
66
|
describe 'stopping at breakpoint' do
|
67
67
|
it 'must stop at the correct line' do
|
68
68
|
enter 'break 14', 'cont'
|
69
|
-
debug_file('
|
69
|
+
debug_file('breakpoint') { $state.line.must_equal 14 }
|
70
70
|
end
|
71
71
|
|
72
72
|
it 'must stop at the correct file' do
|
73
73
|
enter 'break 14', 'cont'
|
74
|
-
debug_file('
|
75
|
-
state.file.must_equal fullpath('
|
74
|
+
debug_file('breakpoint') {
|
75
|
+
$state.file.must_equal fullpath('breakpoint') }
|
76
76
|
end
|
77
77
|
|
78
78
|
describe 'show a message' do
|
@@ -80,9 +80,9 @@ class TestBreakpoints < TestDsl::TestCase
|
|
80
80
|
describe 'with full filename' do
|
81
81
|
it 'must show a message with full filename' do
|
82
82
|
enter 'break 14', 'cont'
|
83
|
-
debug_file('
|
83
|
+
debug_file('breakpoint') { @id = Byebug.breakpoints.first.id }
|
84
84
|
check_output_includes \
|
85
|
-
"Created breakpoint #{@id} at #{fullpath('
|
85
|
+
"Created breakpoint #{@id} at #{fullpath('breakpoint')}:14"
|
86
86
|
end
|
87
87
|
end
|
88
88
|
|
@@ -91,8 +91,8 @@ class TestBreakpoints < TestDsl::TestCase
|
|
91
91
|
|
92
92
|
it 'must show a message with basename' do
|
93
93
|
enter 'break 14', 'cont'
|
94
|
-
debug_file('
|
95
|
-
check_output_includes "Created breakpoint #{@id} at
|
94
|
+
debug_file('breakpoint') { @id = Byebug.breakpoints.first.id }
|
95
|
+
check_output_includes "Created breakpoint #{@id} at breakpoint.rb:14"
|
96
96
|
end
|
97
97
|
end
|
98
98
|
end
|
@@ -105,25 +105,25 @@ class TestBreakpoints < TestDsl::TestCase
|
|
105
105
|
it 'must not reload source' do
|
106
106
|
id = nil
|
107
107
|
enter \
|
108
|
-
->{change_line_in_file(fullpath('
|
109
|
-
->{change_line_in_file(fullpath('
|
108
|
+
->{change_line_in_file(fullpath('breakpoint'), 14, ''); 'break 14'},
|
109
|
+
->{change_line_in_file(fullpath('breakpoint'), 14, 'c = a + b');
|
110
110
|
'cont'}
|
111
|
-
debug_file('
|
111
|
+
debug_file('breakpoint') { id = Byebug.breakpoints.first.id }
|
112
112
|
check_output_includes \
|
113
|
-
"Created breakpoint #{id} at #{fullpath('
|
113
|
+
"Created breakpoint #{id} at #{fullpath('breakpoint')}:14"
|
114
114
|
end
|
115
115
|
end
|
116
116
|
|
117
117
|
describe 'autoreload set' do
|
118
118
|
it 'must reload source' do
|
119
119
|
enter \
|
120
|
-
->{change_line_in_file(fullpath('
|
120
|
+
->{change_line_in_file(fullpath('breakpoint'), 14, ''); 'break 14'},
|
121
121
|
# 2nd breakpoint just to reload source code after rolling changes back
|
122
|
-
->{change_line_in_file(fullpath('
|
122
|
+
->{change_line_in_file(fullpath('breakpoint'), 14, 'c = a + b');
|
123
123
|
'break 15'}, 'cont'
|
124
|
-
debug_file '
|
124
|
+
debug_file 'breakpoint'
|
125
125
|
check_output_includes \
|
126
|
-
"Line 14 is not a stopping point in file #{fullpath('
|
126
|
+
"Line 14 is not a stopping point in file #{fullpath('breakpoint')}",
|
127
127
|
interface.error_queue
|
128
128
|
end
|
129
129
|
end
|
@@ -134,19 +134,19 @@ class TestBreakpoints < TestDsl::TestCase
|
|
134
134
|
before { enter "break #{fullpath('breakpoint2')}:3", 'cont' }
|
135
135
|
|
136
136
|
it 'must stop at the correct line' do
|
137
|
-
debug_file('
|
137
|
+
debug_file('breakpoint') { $state.line.must_equal 3 }
|
138
138
|
end
|
139
139
|
|
140
140
|
it 'must stop at the correct file' do
|
141
|
-
debug_file('
|
142
|
-
state.file.must_equal fullpath('breakpoint2') }
|
141
|
+
debug_file('breakpoint') {
|
142
|
+
$state.file.must_equal fullpath('breakpoint2') }
|
143
143
|
end
|
144
144
|
end
|
145
145
|
|
146
146
|
describe 'when setting breakpoint to unexisted file' do
|
147
147
|
before do
|
148
148
|
enter 'break asf:324'
|
149
|
-
debug_file('
|
149
|
+
debug_file('breakpoint')
|
150
150
|
end
|
151
151
|
it 'must show an error' do
|
152
152
|
check_output_includes 'No source file named asf', interface.error_queue
|
@@ -164,12 +164,12 @@ class TestBreakpoints < TestDsl::TestCase
|
|
164
164
|
before { enter 'break A#b', 'cont' }
|
165
165
|
|
166
166
|
it 'must stop at the correct line' do
|
167
|
-
debug_file('
|
167
|
+
debug_file('breakpoint') { $state.line.must_equal 5 }
|
168
168
|
end
|
169
169
|
|
170
170
|
it 'must stop at the correct file' do
|
171
|
-
debug_file('
|
172
|
-
state.file.must_equal fullpath('
|
171
|
+
debug_file('breakpoint') {
|
172
|
+
$state.file.must_equal fullpath('breakpoint') }
|
173
173
|
end
|
174
174
|
end
|
175
175
|
|
@@ -177,19 +177,19 @@ class TestBreakpoints < TestDsl::TestCase
|
|
177
177
|
before { enter 'break A.a', 'cont' }
|
178
178
|
|
179
179
|
it 'must stop at the correct line' do
|
180
|
-
debug_file('
|
180
|
+
debug_file('breakpoint') { $state.line.must_equal 2 }
|
181
181
|
end
|
182
182
|
|
183
183
|
it 'must stop at the correct file' do
|
184
|
-
debug_file('
|
185
|
-
state.file.must_equal fullpath('
|
184
|
+
debug_file('breakpoint') {
|
185
|
+
$state.file.must_equal fullpath('breakpoint') }
|
186
186
|
end
|
187
187
|
end
|
188
188
|
|
189
189
|
describe 'set breakpoint to unexisted class' do
|
190
190
|
it 'must show an error' do
|
191
191
|
enter 'break B.a'
|
192
|
-
debug_file('
|
192
|
+
debug_file('breakpoint')
|
193
193
|
check_output_includes 'Unknown class B.', interface.error_queue
|
194
194
|
end
|
195
195
|
end
|
@@ -199,11 +199,11 @@ class TestBreakpoints < TestDsl::TestCase
|
|
199
199
|
before { enter 'break foo' }
|
200
200
|
|
201
201
|
it 'must not create a breakpoint' do
|
202
|
-
debug_file('
|
202
|
+
debug_file('breakpoint') { Byebug.breakpoints.must_be_empty }
|
203
203
|
end
|
204
204
|
|
205
205
|
it 'must show an error' do
|
206
|
-
debug_file('
|
206
|
+
debug_file('breakpoint')
|
207
207
|
check_output_includes \
|
208
208
|
'Invalid breakpoint location: foo.', interface.error_queue
|
209
209
|
end
|
@@ -218,13 +218,13 @@ class TestBreakpoints < TestDsl::TestCase
|
|
218
218
|
'break 15' }
|
219
219
|
|
220
220
|
it 'must have a breakpoint with #enabled? returning false' do
|
221
|
-
debug_file('
|
221
|
+
debug_file('breakpoint') {
|
222
222
|
Byebug.breakpoints.first.enabled?.must_equal false }
|
223
223
|
end
|
224
224
|
|
225
225
|
it 'must not stop on the disabled breakpoint' do
|
226
226
|
enter 'cont'
|
227
|
-
debug_file('
|
227
|
+
debug_file('breakpoint') { $state.line.must_equal 15 }
|
228
228
|
end
|
229
229
|
end
|
230
230
|
|
@@ -233,7 +233,7 @@ class TestBreakpoints < TestDsl::TestCase
|
|
233
233
|
'break 15' }
|
234
234
|
|
235
235
|
it 'must have a breakpoint with #enabled? returning false' do
|
236
|
-
debug_file('
|
236
|
+
debug_file('breakpoint') {
|
237
237
|
Byebug.breakpoints.first.enabled?.must_equal false }
|
238
238
|
end
|
239
239
|
end
|
@@ -242,7 +242,7 @@ class TestBreakpoints < TestDsl::TestCase
|
|
242
242
|
describe 'errors' do
|
243
243
|
it 'must show an error if syntax is incorrect' do
|
244
244
|
enter 'disable'
|
245
|
-
debug_file('
|
245
|
+
debug_file('breakpoint')
|
246
246
|
check_output_includes \
|
247
247
|
'"disable" must be followed by "display", "breakpoints" or ' \
|
248
248
|
'breakpoint numbers.', interface.error_queue
|
@@ -250,7 +250,7 @@ class TestBreakpoints < TestDsl::TestCase
|
|
250
250
|
|
251
251
|
it 'must show an error if no breakpoints is set' do
|
252
252
|
enter 'disable 1'
|
253
|
-
debug_file('
|
253
|
+
debug_file('breakpoint')
|
254
254
|
check_output_includes \
|
255
255
|
'No breakpoints have been set.', interface.error_queue
|
256
256
|
end
|
@@ -258,7 +258,7 @@ class TestBreakpoints < TestDsl::TestCase
|
|
258
258
|
it 'must show an error if not a number is provided as an argument to ' \
|
259
259
|
' "disable" command' do
|
260
260
|
enter 'break 14', 'disable foo'
|
261
|
-
debug_file('
|
261
|
+
debug_file('breakpoint')
|
262
262
|
check_output_includes \
|
263
263
|
'Disable breakpoints argument "foo" needs to be a number.'
|
264
264
|
end
|
@@ -274,13 +274,13 @@ class TestBreakpoints < TestDsl::TestCase
|
|
274
274
|
before { enter ->{"enable #{Byebug.breakpoints.first.id}"}, 'break 15' }
|
275
275
|
|
276
276
|
it 'must have a breakpoint with #enabled? returning true' do
|
277
|
-
debug_file('
|
277
|
+
debug_file('breakpoint') {
|
278
278
|
Byebug.breakpoints.first.enabled?.must_equal true }
|
279
279
|
end
|
280
280
|
|
281
281
|
it 'must stop on the enabled breakpoint' do
|
282
282
|
enter 'cont'
|
283
|
-
debug_file('
|
283
|
+
debug_file('breakpoint') { $state.line.must_equal 14 }
|
284
284
|
end
|
285
285
|
end
|
286
286
|
|
@@ -289,7 +289,7 @@ class TestBreakpoints < TestDsl::TestCase
|
|
289
289
|
'break 15' }
|
290
290
|
|
291
291
|
it 'must have a breakpoint with #enabled? returning true' do
|
292
|
-
debug_file('
|
292
|
+
debug_file('breakpoint') {
|
293
293
|
Byebug.breakpoints.first.enabled?.must_equal true }
|
294
294
|
end
|
295
295
|
end
|
@@ -298,7 +298,7 @@ class TestBreakpoints < TestDsl::TestCase
|
|
298
298
|
describe 'errors' do
|
299
299
|
it 'must show an error if syntax is incorrect' do
|
300
300
|
enter 'enable'
|
301
|
-
debug_file('
|
301
|
+
debug_file('breakpoint')
|
302
302
|
check_output_includes \
|
303
303
|
'"enable" must be followed by "display", "breakpoints" or ' \
|
304
304
|
'breakpoint numbers.', interface.error_queue
|
@@ -311,29 +311,29 @@ class TestBreakpoints < TestDsl::TestCase
|
|
311
311
|
'break 15' }
|
312
312
|
|
313
313
|
it 'must have only one breakpoint' do
|
314
|
-
debug_file('
|
314
|
+
debug_file('breakpoint') { Byebug.breakpoints.size.must_equal 1 }
|
315
315
|
end
|
316
316
|
|
317
317
|
it 'must not stop on the disabled breakpoint' do
|
318
318
|
enter 'cont'
|
319
|
-
debug_file('
|
319
|
+
debug_file('breakpoint') { $state.line.must_equal 15 }
|
320
320
|
end
|
321
321
|
end
|
322
322
|
|
323
323
|
describe 'Conditional breakpoints' do
|
324
324
|
it 'must stop if the condition is true' do
|
325
325
|
enter 'break 14 if b == 5', 'break 15', 'cont'
|
326
|
-
debug_file('
|
326
|
+
debug_file('breakpoint') { $state.line.must_equal 14 }
|
327
327
|
end
|
328
328
|
|
329
329
|
it 'must skip if the condition is false' do
|
330
330
|
enter 'break 14 if b == 3', 'break 15', 'cont'
|
331
|
-
debug_file('
|
331
|
+
debug_file('breakpoint') { $state.line.must_equal 15 }
|
332
332
|
end
|
333
333
|
|
334
334
|
it 'must show an error when conditional syntax is wrong' do
|
335
335
|
enter 'break 14 ifa b == 3', 'break 15', 'cont'
|
336
|
-
debug_file('
|
336
|
+
debug_file('breakpoint') { $state.line.must_equal 15 }
|
337
337
|
check_output_includes \
|
338
338
|
'Expecting "if" in breakpoint condition; got: ifa b == 3.',
|
339
339
|
interface.error_queue
|
@@ -346,12 +346,12 @@ class TestBreakpoints < TestDsl::TestCase
|
|
346
346
|
->{"enable #{Byebug.breakpoints.first.id}"} }
|
347
347
|
|
348
348
|
it 'must not enable a breakpoint' do
|
349
|
-
debug_file('
|
349
|
+
debug_file('breakpoint') {
|
350
350
|
Byebug.breakpoints.first.enabled?.must_equal false }
|
351
351
|
end
|
352
352
|
|
353
353
|
it 'must show an error' do
|
354
|
-
debug_file('
|
354
|
+
debug_file('breakpoint')
|
355
355
|
check_output_includes \
|
356
356
|
'Expression "b -=( 3" syntactically incorrect; breakpoint remains ' \
|
357
357
|
'disabled.', interface.error_queue
|
@@ -360,24 +360,38 @@ class TestBreakpoints < TestDsl::TestCase
|
|
360
360
|
|
361
361
|
it 'must show an error if no file or line is specified' do
|
362
362
|
enter 'break ifa b == 3', 'break 15', 'cont'
|
363
|
-
debug_file('
|
363
|
+
debug_file('breakpoint') { $state.line.must_equal 15 }
|
364
364
|
check_output_includes \
|
365
365
|
'Invalid breakpoint location: ifa b == 3.', interface.error_queue
|
366
366
|
end
|
367
367
|
|
368
368
|
it 'must show an error if expression syntax is invalid' do
|
369
369
|
enter 'break if b -=) 3', 'break 15', 'cont'
|
370
|
-
debug_file('
|
370
|
+
debug_file('breakpoint') { $state.line.must_equal 15 }
|
371
371
|
check_output_includes \
|
372
372
|
'Expression "b -=) 3" syntactically incorrect; breakpoint disabled.',
|
373
373
|
interface.error_queue
|
374
374
|
end
|
375
375
|
end
|
376
376
|
|
377
|
+
describe 'Stopping through `byebug` keyword' do
|
378
|
+
describe 'when not the last instruction of a method' do
|
379
|
+
it 'must stop in the next line' do
|
380
|
+
debug_file('breakpoint') { $state.line.must_equal 13 }
|
381
|
+
end
|
382
|
+
end
|
383
|
+
|
384
|
+
describe 'when last instruction of a method' do
|
385
|
+
it 'must stop right before returning from the frame' do
|
386
|
+
debug_file('breakpoint_deep') { $state.line.must_equal 16 }
|
387
|
+
end
|
388
|
+
end
|
389
|
+
end
|
390
|
+
|
377
391
|
describe 'Help' do
|
378
392
|
it 'must show info about setting breakpoints when using just "break"' do
|
379
393
|
enter 'break', 'cont'
|
380
|
-
debug_file '
|
394
|
+
debug_file 'breakpoint'
|
381
395
|
check_output_includes /b\[reak\] file:line \[if expr\]/
|
382
396
|
end
|
383
397
|
end
|
@@ -385,7 +399,7 @@ class TestBreakpoints < TestDsl::TestCase
|
|
385
399
|
describe 'Post Mortem' do
|
386
400
|
it 'must be able to set breakpoints in post-mortem mode' do
|
387
401
|
enter 'cont', 'break 12', 'cont'
|
388
|
-
debug_file('post_mortem') { state.line.must_equal 12 }
|
402
|
+
debug_file('post_mortem') { $state.line.must_equal 12 }
|
389
403
|
end
|
390
404
|
end
|
391
405
|
|