[ruby/irb] Support repeating debugger input by passing empty input
to it (https://github.com/ruby/irb/pull/856) * Test IRB's behaviour with empty input * Handle empty input and pass it to debugger Since `rdbg` accepts empty input to repeat the previous command, IRB should take empty input in `irb:rdbg` sessions and pass them to the debugger. Currently, IRB simply ignores empty input and does nothing. This commit creates `EmptyInput` to represent empty input so it can fit into the current IRB's input processing flow in `Irb#eval_input`. https://github.com/ruby/irb/commit/0e9db419be
This commit is contained in:
parent
ff4f5c0cdd
commit
b315826377
@ -1082,16 +1082,17 @@ module IRB
|
||||
loop do
|
||||
code = readmultiline
|
||||
break unless code
|
||||
|
||||
if code != "\n"
|
||||
yield build_statement(code), @line_no
|
||||
end
|
||||
yield build_statement(code), @line_no
|
||||
@line_no += code.count("\n")
|
||||
rescue RubyLex::TerminateLineInput
|
||||
end
|
||||
end
|
||||
|
||||
def build_statement(code)
|
||||
if code.match?(/\A\n*\z/)
|
||||
return Statement::EmptyInput.new
|
||||
end
|
||||
|
||||
code.force_encoding(@context.io.encoding)
|
||||
command_or_alias, arg = code.split(/\s/, 2)
|
||||
# Transform a non-identifier alias (@, $) or keywords (next, break)
|
||||
|
@ -20,6 +20,29 @@ module IRB
|
||||
raise NotImplementedError
|
||||
end
|
||||
|
||||
class EmptyInput < Statement
|
||||
def is_assignment?
|
||||
false
|
||||
end
|
||||
|
||||
def suppresses_echo?
|
||||
true
|
||||
end
|
||||
|
||||
# Debugger takes empty input to repeat the last command
|
||||
def should_be_handled_by_debugger?
|
||||
true
|
||||
end
|
||||
|
||||
def code
|
||||
""
|
||||
end
|
||||
|
||||
def evaluable_code
|
||||
code
|
||||
end
|
||||
end
|
||||
|
||||
class Expression < Statement
|
||||
def initialize(code, is_assignment)
|
||||
@code = code
|
||||
|
@ -6,7 +6,7 @@ require "tmpdir"
|
||||
require_relative "helper"
|
||||
|
||||
module TestIRB
|
||||
class DebugCommandTest < IntegrationTestCase
|
||||
class DebuggerIntegrationTest < IntegrationTestCase
|
||||
def setup
|
||||
super
|
||||
|
||||
@ -434,5 +434,29 @@ module TestIRB
|
||||
assert_match(/irb\(main\):001> next/, output)
|
||||
assert_include(output, "Multi-IRB commands are not available when the debugger is enabled.")
|
||||
end
|
||||
|
||||
def test_irb_passes_empty_input_to_debugger_to_repeat_the_last_command
|
||||
write_ruby <<~'ruby'
|
||||
binding.irb
|
||||
puts "foo"
|
||||
puts "bar"
|
||||
puts "baz"
|
||||
ruby
|
||||
|
||||
output = run_ruby_file do
|
||||
type "next"
|
||||
type ""
|
||||
# Test that empty input doesn't repeat expressions
|
||||
type "123"
|
||||
type ""
|
||||
type "next"
|
||||
type ""
|
||||
type ""
|
||||
end
|
||||
|
||||
assert_include(output, "=> 2\| puts \"foo\"")
|
||||
assert_include(output, "=> 3\| puts \"bar\"")
|
||||
assert_include(output, "=> 4\| puts \"baz\"")
|
||||
end
|
||||
end
|
||||
end
|
@ -58,6 +58,24 @@ module TestIRB
|
||||
assert_include output, "=> \"It's a foo\""
|
||||
assert_include output, "=> \"It's a bar\""
|
||||
end
|
||||
|
||||
def test_empty_input_echoing_behaviour
|
||||
write_ruby <<~'RUBY'
|
||||
binding.irb
|
||||
RUBY
|
||||
|
||||
output = run_ruby_file do
|
||||
type ""
|
||||
type " "
|
||||
type "exit"
|
||||
end
|
||||
|
||||
# Input cramped together due to how Reline's Reline::GeneralIO works
|
||||
assert_include(
|
||||
output,
|
||||
"irb(main):001> irb(main):002> irb(main):002> irb(main):002> => nil\r\n"
|
||||
)
|
||||
end
|
||||
end
|
||||
|
||||
class IrbIOConfigurationTest < TestCase
|
||||
|
Loading…
x
Reference in New Issue
Block a user