irb 1.6.4 → 1.8.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/Gemfile +1 -0
- data/README.md +135 -14
- data/Rakefile +0 -7
- data/doc/irb/irb.rd.ja +1 -3
- data/irb.gemspec +2 -1
- data/lib/irb/cmd/chws.rb +2 -2
- data/lib/irb/cmd/debug.rb +36 -92
- data/lib/irb/cmd/edit.rb +6 -7
- data/lib/irb/cmd/help.rb +12 -46
- data/lib/irb/cmd/irb_info.rb +14 -18
- data/lib/irb/cmd/ls.rb +17 -7
- data/lib/irb/cmd/nop.rb +4 -8
- data/lib/irb/cmd/pushws.rb +3 -3
- data/lib/irb/cmd/show_cmds.rb +17 -3
- data/lib/irb/cmd/show_doc.rb +48 -0
- data/lib/irb/cmd/show_source.rb +4 -60
- data/lib/irb/cmd/subirb.rb +49 -6
- data/lib/irb/color.rb +2 -0
- data/lib/irb/completion.rb +2 -2
- data/lib/irb/context.rb +52 -21
- data/lib/irb/debug/ui.rb +104 -0
- data/lib/irb/debug.rb +115 -0
- data/lib/irb/ext/{history.rb → eval_history.rb} +4 -4
- data/lib/irb/ext/loader.rb +2 -0
- data/lib/irb/ext/tracer.rb +1 -1
- data/lib/irb/extend-command.rb +7 -5
- data/lib/irb/help.rb +1 -3
- data/lib/irb/{ext/save-history.rb → history.rb} +4 -55
- data/lib/irb/init.rb +4 -10
- data/lib/irb/input-method.rb +65 -131
- data/lib/irb/locale.rb +10 -43
- data/lib/irb/nesting_parser.rb +227 -0
- data/lib/irb/pager.rb +86 -0
- data/lib/irb/ruby-lex.rb +401 -747
- data/lib/irb/source_finder.rb +64 -0
- data/lib/irb/statement.rb +80 -0
- data/lib/irb/version.rb +2 -2
- data/lib/irb/workspace.rb +4 -0
- data/lib/irb.rb +222 -120
- metadata +28 -11
- data/lib/irb/cmd/fork.rb +0 -34
- data/lib/irb/lc/ja/encoding_aliases.rb +0 -13
- data/lib/irb/magic-file.rb +0 -38
- data/lib/irb/src_encoding.rb +0 -7
data/lib/irb/debug.rb
ADDED
@@ -0,0 +1,115 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module IRB
|
4
|
+
module Debug
|
5
|
+
IRB_DIR = File.expand_path('..', __dir__)
|
6
|
+
|
7
|
+
class << self
|
8
|
+
def insert_debug_break(pre_cmds: nil, do_cmds: nil)
|
9
|
+
options = { oneshot: true, hook_call: false }
|
10
|
+
|
11
|
+
if pre_cmds || do_cmds
|
12
|
+
options[:command] = ['irb', pre_cmds, do_cmds]
|
13
|
+
end
|
14
|
+
if DEBUGGER__::LineBreakpoint.instance_method(:initialize).parameters.include?([:key, :skip_src])
|
15
|
+
options[:skip_src] = true
|
16
|
+
end
|
17
|
+
|
18
|
+
# To make debugger commands like `next` or `continue` work without asking
|
19
|
+
# the user to quit IRB after that, we need to exit IRB first and then hit
|
20
|
+
# a TracePoint on #debug_break.
|
21
|
+
file, lineno = IRB::Irb.instance_method(:debug_break).source_location
|
22
|
+
DEBUGGER__::SESSION.add_line_breakpoint(file, lineno + 1, **options)
|
23
|
+
end
|
24
|
+
|
25
|
+
def setup(irb)
|
26
|
+
# When debug session is not started at all
|
27
|
+
unless defined?(DEBUGGER__::SESSION)
|
28
|
+
begin
|
29
|
+
require "debug/session"
|
30
|
+
rescue LoadError # debug.gem is not written in Gemfile
|
31
|
+
return false unless load_bundled_debug_gem
|
32
|
+
end
|
33
|
+
DEBUGGER__::CONFIG.set_config
|
34
|
+
configure_irb_for_debugger(irb)
|
35
|
+
thread = Thread.current
|
36
|
+
|
37
|
+
DEBUGGER__.initialize_session{ IRB::Debug::UI.new(thread, irb) }
|
38
|
+
end
|
39
|
+
|
40
|
+
# When debug session was previously started but not by IRB
|
41
|
+
if defined?(DEBUGGER__::SESSION) && !irb.context.with_debugger
|
42
|
+
configure_irb_for_debugger(irb)
|
43
|
+
thread = Thread.current
|
44
|
+
|
45
|
+
DEBUGGER__::SESSION.reset_ui(IRB::Debug::UI.new(thread, irb))
|
46
|
+
end
|
47
|
+
|
48
|
+
# Apply patches to debug gem so it skips IRB frames
|
49
|
+
unless DEBUGGER__.respond_to?(:capture_frames_without_irb)
|
50
|
+
DEBUGGER__.singleton_class.send(:alias_method, :capture_frames_without_irb, :capture_frames)
|
51
|
+
|
52
|
+
def DEBUGGER__.capture_frames(*args)
|
53
|
+
frames = capture_frames_without_irb(*args)
|
54
|
+
frames.reject! do |frame|
|
55
|
+
frame.realpath&.start_with?(IRB_DIR) || frame.path == "<internal:prelude>"
|
56
|
+
end
|
57
|
+
frames
|
58
|
+
end
|
59
|
+
|
60
|
+
DEBUGGER__::ThreadClient.prepend(SkipPathHelperForIRB)
|
61
|
+
end
|
62
|
+
|
63
|
+
true
|
64
|
+
end
|
65
|
+
|
66
|
+
private
|
67
|
+
|
68
|
+
def configure_irb_for_debugger(irb)
|
69
|
+
require 'irb/debug/ui'
|
70
|
+
IRB.instance_variable_set(:@debugger_irb, irb)
|
71
|
+
irb.context.with_debugger = true
|
72
|
+
irb.context.irb_name += ":rdbg"
|
73
|
+
end
|
74
|
+
|
75
|
+
module SkipPathHelperForIRB
|
76
|
+
def skip_internal_path?(path)
|
77
|
+
# The latter can be removed once https://github.com/ruby/debug/issues/866 is resolved
|
78
|
+
super || path.match?(IRB_DIR) || path.match?('<internal:prelude>')
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
82
|
+
# This is used when debug.gem is not written in Gemfile. Even if it's not
|
83
|
+
# installed by `bundle install`, debug.gem is installed by default because
|
84
|
+
# it's a bundled gem. This method tries to activate and load that.
|
85
|
+
def load_bundled_debug_gem
|
86
|
+
# Discover latest debug.gem under GEM_PATH
|
87
|
+
debug_gem = Gem.paths.path.flat_map { |path| Dir.glob("#{path}/gems/debug-*") }.select do |path|
|
88
|
+
File.basename(path).match?(/\Adebug-\d+\.\d+\.\d+(\w+)?\z/)
|
89
|
+
end.sort_by do |path|
|
90
|
+
Gem::Version.new(File.basename(path).delete_prefix('debug-'))
|
91
|
+
end.last
|
92
|
+
return false unless debug_gem
|
93
|
+
|
94
|
+
# Discover debug/debug.so under extensions for Ruby 3.2+
|
95
|
+
ext_name = "/debug/debug.#{RbConfig::CONFIG['DLEXT']}"
|
96
|
+
ext_path = Gem.paths.path.flat_map do |path|
|
97
|
+
Dir.glob("#{path}/extensions/**/#{File.basename(debug_gem)}#{ext_name}")
|
98
|
+
end.first
|
99
|
+
|
100
|
+
# Attempt to forcibly load the bundled gem
|
101
|
+
if ext_path
|
102
|
+
$LOAD_PATH << ext_path.delete_suffix(ext_name)
|
103
|
+
end
|
104
|
+
$LOAD_PATH << "#{debug_gem}/lib"
|
105
|
+
begin
|
106
|
+
require "debug/session"
|
107
|
+
puts "Loaded #{File.basename(debug_gem)}"
|
108
|
+
true
|
109
|
+
rescue LoadError
|
110
|
+
false
|
111
|
+
end
|
112
|
+
end
|
113
|
+
end
|
114
|
+
end
|
115
|
+
end
|
@@ -40,14 +40,14 @@ module IRB # :nodoc:
|
|
40
40
|
#
|
41
41
|
# If +no+ is +nil+, execution result history isn't used (default).
|
42
42
|
#
|
43
|
-
#
|
44
|
-
# IRB::
|
43
|
+
# EvalHistory values are available via <code>__</code> variable, see
|
44
|
+
# IRB::EvalHistory.
|
45
45
|
def eval_history=(no)
|
46
46
|
if no
|
47
47
|
if defined?(@eval_history) && @eval_history
|
48
48
|
@eval_history_values.size(no)
|
49
49
|
else
|
50
|
-
@eval_history_values =
|
50
|
+
@eval_history_values = EvalHistory.new(no)
|
51
51
|
IRB.conf[:__TMP__EHV__] = @eval_history_values
|
52
52
|
@workspace.evaluate("__ = IRB.conf[:__TMP__EHV__]")
|
53
53
|
IRB.conf.delete(:__TMP_EHV__)
|
@@ -89,7 +89,7 @@ module IRB # :nodoc:
|
|
89
89
|
# __[1]
|
90
90
|
# # => 10
|
91
91
|
#
|
92
|
-
class
|
92
|
+
class EvalHistory
|
93
93
|
|
94
94
|
def initialize(size = 16) # :nodoc:
|
95
95
|
@size = size
|
data/lib/irb/ext/loader.rb
CHANGED
@@ -42,6 +42,7 @@ module IRB # :nodoc:
|
|
42
42
|
#
|
43
43
|
# See Irb#suspend_input_method for more information.
|
44
44
|
def source_file(path)
|
45
|
+
irb = irb_context.irb
|
45
46
|
irb.suspend_name(path, File.basename(path)) do
|
46
47
|
FileInputMethod.open(path) do |io|
|
47
48
|
irb.suspend_input_method(io) do
|
@@ -66,6 +67,7 @@ module IRB # :nodoc:
|
|
66
67
|
#
|
67
68
|
# See Irb#suspend_input_method for more information.
|
68
69
|
def load_file(path, priv = nil)
|
70
|
+
irb = irb_context.irb
|
69
71
|
irb.suspend_name(path, File.basename(path)) do
|
70
72
|
|
71
73
|
if priv
|
data/lib/irb/ext/tracer.rb
CHANGED
@@ -7,7 +7,7 @@
|
|
7
7
|
begin
|
8
8
|
require "tracer"
|
9
9
|
rescue LoadError
|
10
|
-
$stderr.puts "Tracer extension of IRB is enabled but tracer gem
|
10
|
+
$stderr.puts "Tracer extension of IRB is enabled but tracer gem wasn't found."
|
11
11
|
module IRB
|
12
12
|
class Context
|
13
13
|
def use_tracer=(opt)
|
data/lib/irb/extend-command.rb
CHANGED
@@ -157,10 +157,14 @@ module IRB # :nodoc:
|
|
157
157
|
|
158
158
|
[
|
159
159
|
:irb_help, :Help, "cmd/help",
|
160
|
-
[:show_doc, NO_OVERRIDE],
|
161
160
|
[:help, NO_OVERRIDE],
|
162
161
|
],
|
163
162
|
|
163
|
+
[
|
164
|
+
:irb_show_doc, :ShowDoc, "cmd/show_doc",
|
165
|
+
[:show_doc, NO_OVERRIDE],
|
166
|
+
],
|
167
|
+
|
164
168
|
[
|
165
169
|
:irb_info, :IrbInfo, "cmd/irb_info"
|
166
170
|
],
|
@@ -285,7 +289,7 @@ module IRB # :nodoc:
|
|
285
289
|
alias_method to, from
|
286
290
|
}
|
287
291
|
else
|
288
|
-
Kernel.
|
292
|
+
Kernel.warn "irb: warn: can't alias #{to} from #{from}.\n"
|
289
293
|
end
|
290
294
|
end
|
291
295
|
|
@@ -312,10 +316,9 @@ module IRB # :nodoc:
|
|
312
316
|
CE = ContextExtender # :nodoc:
|
313
317
|
|
314
318
|
@EXTEND_COMMANDS = [
|
315
|
-
[:eval_history=, "ext/
|
319
|
+
[:eval_history=, "ext/eval_history.rb"],
|
316
320
|
[:use_tracer=, "ext/tracer.rb"],
|
317
321
|
[:use_loader=, "ext/use-loader.rb"],
|
318
|
-
[:save_history=, "ext/save-history.rb"],
|
319
322
|
]
|
320
323
|
|
321
324
|
# Installs the default context extensions as irb commands:
|
@@ -323,7 +326,6 @@ module IRB # :nodoc:
|
|
323
326
|
# Context#eval_history=:: +irb/ext/history.rb+
|
324
327
|
# Context#use_tracer=:: +irb/ext/tracer.rb+
|
325
328
|
# Context#use_loader=:: +irb/ext/use-loader.rb+
|
326
|
-
# Context#save_history=:: +irb/ext/save-history.rb+
|
327
329
|
def self.install_extend_commands
|
328
330
|
for args in @EXTEND_COMMANDS
|
329
331
|
def_extend_command(*args)
|
data/lib/irb/help.rb
CHANGED
@@ -4,15 +4,13 @@
|
|
4
4
|
# by Keiju ISHITSUKA(keiju@ishitsuka.com)
|
5
5
|
#
|
6
6
|
|
7
|
-
require_relative 'magic-file'
|
8
|
-
|
9
7
|
module IRB
|
10
8
|
# Outputs the irb help message, see IRB@Command+line+options.
|
11
9
|
def IRB.print_usage
|
12
10
|
lc = IRB.conf[:LC_MESSAGES]
|
13
11
|
path = lc.find("irb/help-message")
|
14
12
|
space_line = false
|
15
|
-
|
13
|
+
File.open(path){|f|
|
16
14
|
f.each_line do |l|
|
17
15
|
if /^\s*$/ =~ l
|
18
16
|
lc.puts l unless space_line
|
@@ -1,64 +1,14 @@
|
|
1
|
-
# frozen_string_literal: false
|
2
|
-
#
|
3
|
-
# save-history.rb -
|
4
|
-
# by Keiju ISHITSUKA(keiju@ruby-lang.org)
|
5
|
-
#
|
6
|
-
|
7
1
|
module IRB
|
8
2
|
module HistorySavingAbility # :nodoc:
|
9
|
-
|
10
|
-
|
11
|
-
class Context
|
12
|
-
def init_save_history# :nodoc:
|
13
|
-
unless (class<<@io;self;end).include?(HistorySavingAbility)
|
14
|
-
@io.extend(HistorySavingAbility)
|
15
|
-
end
|
16
|
-
end
|
17
|
-
|
18
|
-
# A copy of the default <code>IRB.conf[:SAVE_HISTORY]</code>
|
19
|
-
def save_history
|
20
|
-
IRB.conf[:SAVE_HISTORY]
|
21
|
-
end
|
22
|
-
|
23
|
-
remove_method(:save_history=) if method_defined?(:save_history=)
|
24
|
-
# Sets <code>IRB.conf[:SAVE_HISTORY]</code> to the given +val+ and calls
|
25
|
-
# #init_save_history with this context.
|
26
|
-
#
|
27
|
-
# Will store the number of +val+ entries of history in the #history_file
|
28
|
-
#
|
29
|
-
# Add the following to your +.irbrc+ to change the number of history
|
30
|
-
# entries stored to 1000:
|
31
|
-
#
|
32
|
-
# IRB.conf[:SAVE_HISTORY] = 1000
|
33
|
-
def save_history=(val)
|
34
|
-
IRB.conf[:SAVE_HISTORY] = val
|
35
|
-
if val
|
36
|
-
main_context = IRB.conf[:MAIN_CONTEXT]
|
37
|
-
main_context = self unless main_context
|
38
|
-
main_context.init_save_history
|
39
|
-
end
|
40
|
-
end
|
41
|
-
|
42
|
-
# A copy of the default <code>IRB.conf[:HISTORY_FILE]</code>
|
43
|
-
def history_file
|
44
|
-
IRB.conf[:HISTORY_FILE]
|
3
|
+
def support_history_saving?
|
4
|
+
true
|
45
5
|
end
|
46
6
|
|
47
|
-
|
48
|
-
|
49
|
-
IRB.conf[:HISTORY_FILE] = hist
|
50
|
-
end
|
51
|
-
end
|
52
|
-
|
53
|
-
module HistorySavingAbility # :nodoc:
|
54
|
-
def HistorySavingAbility.extended(obj)
|
55
|
-
IRB.conf[:AT_EXIT].push proc{obj.save_history}
|
56
|
-
obj.load_history
|
57
|
-
obj
|
7
|
+
def reset_history_counter
|
8
|
+
@loaded_history_lines = self.class::HISTORY.size if defined? @loaded_history_lines
|
58
9
|
end
|
59
10
|
|
60
11
|
def load_history
|
61
|
-
return unless self.class.const_defined?(:HISTORY)
|
62
12
|
history = self.class::HISTORY
|
63
13
|
if history_file = IRB.conf[:HISTORY_FILE]
|
64
14
|
history_file = File.expand_path(history_file)
|
@@ -82,7 +32,6 @@ module IRB
|
|
82
32
|
end
|
83
33
|
|
84
34
|
def save_history
|
85
|
-
return unless self.class.const_defined?(:HISTORY)
|
86
35
|
history = self.class::HISTORY
|
87
36
|
if num = IRB.conf[:SAVE_HISTORY] and (num = num.to_i) != 0
|
88
37
|
if history_file = IRB.conf[:HISTORY_FILE]
|
data/lib/irb/init.rb
CHANGED
@@ -58,35 +58,30 @@ module IRB # :nodoc:
|
|
58
58
|
@CONF[:PROMPT] = {
|
59
59
|
:NULL => {
|
60
60
|
:PROMPT_I => nil,
|
61
|
-
:PROMPT_N => nil,
|
62
61
|
:PROMPT_S => nil,
|
63
62
|
:PROMPT_C => nil,
|
64
63
|
:RETURN => "%s\n"
|
65
64
|
},
|
66
65
|
:DEFAULT => {
|
67
|
-
:PROMPT_I => "%N(%m):%03n
|
68
|
-
:
|
69
|
-
:
|
70
|
-
:PROMPT_C => "%N(%m):%03n:%i* ",
|
66
|
+
:PROMPT_I => "%N(%m):%03n> ",
|
67
|
+
:PROMPT_S => "%N(%m):%03n%l ",
|
68
|
+
:PROMPT_C => "%N(%m):%03n* ",
|
71
69
|
:RETURN => "=> %s\n"
|
72
70
|
},
|
73
71
|
:CLASSIC => {
|
74
72
|
:PROMPT_I => "%N(%m):%03n:%i> ",
|
75
|
-
:PROMPT_N => "%N(%m):%03n:%i> ",
|
76
73
|
:PROMPT_S => "%N(%m):%03n:%i%l ",
|
77
74
|
:PROMPT_C => "%N(%m):%03n:%i* ",
|
78
75
|
:RETURN => "%s\n"
|
79
76
|
},
|
80
77
|
:SIMPLE => {
|
81
78
|
:PROMPT_I => ">> ",
|
82
|
-
:PROMPT_N => ">> ",
|
83
79
|
:PROMPT_S => "%l> ",
|
84
80
|
:PROMPT_C => "?> ",
|
85
81
|
:RETURN => "=> %s\n"
|
86
82
|
},
|
87
83
|
:INF_RUBY => {
|
88
|
-
:PROMPT_I => "%N(%m):%03n
|
89
|
-
:PROMPT_N => nil,
|
84
|
+
:PROMPT_I => "%N(%m):%03n> ",
|
90
85
|
:PROMPT_S => nil,
|
91
86
|
:PROMPT_C => nil,
|
92
87
|
:RETURN => "%s\n",
|
@@ -94,7 +89,6 @@ module IRB # :nodoc:
|
|
94
89
|
},
|
95
90
|
:XMP => {
|
96
91
|
:PROMPT_I => nil,
|
97
|
-
:PROMPT_N => nil,
|
98
92
|
:PROMPT_S => nil,
|
99
93
|
:PROMPT_C => nil,
|
100
94
|
:RETURN => " ==>%s\n"
|
data/lib/irb/input-method.rb
CHANGED
@@ -4,23 +4,13 @@
|
|
4
4
|
# by Keiju ISHITSUKA(keiju@ruby-lang.org)
|
5
5
|
#
|
6
6
|
|
7
|
-
require_relative 'src_encoding'
|
8
|
-
require_relative 'magic-file'
|
9
7
|
require_relative 'completion'
|
8
|
+
require_relative "history"
|
10
9
|
require 'io/console'
|
11
10
|
require 'reline'
|
12
11
|
|
13
12
|
module IRB
|
14
|
-
STDIN_FILE_NAME = "(line)" # :nodoc:
|
15
13
|
class InputMethod
|
16
|
-
|
17
|
-
# Creates a new input method object
|
18
|
-
def initialize(file = STDIN_FILE_NAME)
|
19
|
-
@file_name = file
|
20
|
-
end
|
21
|
-
# The file name of this input method, usually given during initialization.
|
22
|
-
attr_reader :file_name
|
23
|
-
|
24
14
|
# The irb prompt associated with this input method
|
25
15
|
attr_accessor :prompt
|
26
16
|
|
@@ -48,6 +38,10 @@ module IRB
|
|
48
38
|
false
|
49
39
|
end
|
50
40
|
|
41
|
+
def support_history_saving?
|
42
|
+
false
|
43
|
+
end
|
44
|
+
|
51
45
|
# For debug message
|
52
46
|
def inspect
|
53
47
|
'Abstract InputMethod'
|
@@ -57,7 +51,6 @@ module IRB
|
|
57
51
|
class StdioInputMethod < InputMethod
|
58
52
|
# Creates a new input method object
|
59
53
|
def initialize
|
60
|
-
super
|
61
54
|
@line_no = 0
|
62
55
|
@line = []
|
63
56
|
@stdin = IO.open(STDIN.to_i, :external_encoding => IRB.conf[:LC_MESSAGES].encoding, :internal_encoding => "-")
|
@@ -131,12 +124,9 @@ module IRB
|
|
131
124
|
|
132
125
|
# Creates a new input method object
|
133
126
|
def initialize(file)
|
134
|
-
|
135
|
-
@io = file.is_a?(IO) ? file : IRB::MagicFile.open(file)
|
127
|
+
@io = file.is_a?(IO) ? file : File.open(file)
|
136
128
|
@external_encoding = @io.external_encoding
|
137
129
|
end
|
138
|
-
# The file name of this input method, usually given during initialization.
|
139
|
-
attr_reader :file_name
|
140
130
|
|
141
131
|
# Whether the end of this input method has been reached, returns +true+ if
|
142
132
|
# there is no more data to read.
|
@@ -169,111 +159,79 @@ module IRB
|
|
169
159
|
end
|
170
160
|
end
|
171
161
|
|
172
|
-
|
173
|
-
|
174
|
-
|
175
|
-
|
176
|
-
|
177
|
-
|
178
|
-
|
179
|
-
end
|
180
|
-
|
181
|
-
# Creates a new input method object using Readline
|
182
|
-
def initialize
|
183
|
-
self.class.initialize_readline
|
184
|
-
if Readline.respond_to?(:encoding_system_needs)
|
185
|
-
IRB.__send__(:set_encoding, Readline.encoding_system_needs.name, override: false)
|
186
|
-
end
|
187
|
-
super
|
188
|
-
|
189
|
-
@line_no = 0
|
190
|
-
@line = []
|
191
|
-
@eof = false
|
162
|
+
class ReadlineInputMethod < StdioInputMethod
|
163
|
+
def self.initialize_readline
|
164
|
+
require "readline"
|
165
|
+
rescue LoadError
|
166
|
+
else
|
167
|
+
include ::Readline
|
168
|
+
end
|
192
169
|
|
193
|
-
|
194
|
-
@stdout = IO.open(STDOUT.to_i, 'w', :external_encoding => IRB.conf[:LC_MESSAGES].encoding, :internal_encoding => "-")
|
170
|
+
include HistorySavingAbility
|
195
171
|
|
196
|
-
|
197
|
-
|
198
|
-
|
199
|
-
|
200
|
-
Readline.
|
172
|
+
# Creates a new input method object using Readline
|
173
|
+
def initialize
|
174
|
+
self.class.initialize_readline
|
175
|
+
if Readline.respond_to?(:encoding_system_needs)
|
176
|
+
IRB.__send__(:set_encoding, Readline.encoding_system_needs.name, override: false)
|
201
177
|
end
|
202
178
|
|
203
|
-
|
204
|
-
#
|
205
|
-
# See IO#gets for more information.
|
206
|
-
def gets
|
207
|
-
Readline.input = @stdin
|
208
|
-
Readline.output = @stdout
|
209
|
-
if l = readline(@prompt, false)
|
210
|
-
HISTORY.push(l) if !l.empty?
|
211
|
-
@line[@line_no += 1] = l + "\n"
|
212
|
-
else
|
213
|
-
@eof = true
|
214
|
-
l
|
215
|
-
end
|
216
|
-
end
|
179
|
+
super
|
217
180
|
|
218
|
-
|
219
|
-
# if there is no more data to read.
|
220
|
-
#
|
221
|
-
# See IO#eof? for more information.
|
222
|
-
def eof?
|
223
|
-
@eof
|
224
|
-
end
|
181
|
+
@eof = false
|
225
182
|
|
226
|
-
|
227
|
-
|
228
|
-
#
|
229
|
-
# See IO#eof for more information.
|
230
|
-
def readable_after_eof?
|
231
|
-
true
|
183
|
+
if Readline.respond_to?("basic_word_break_characters=")
|
184
|
+
Readline.basic_word_break_characters = IRB::InputCompletor::BASIC_WORD_BREAK_CHARACTERS
|
232
185
|
end
|
186
|
+
Readline.completion_append_character = nil
|
187
|
+
Readline.completion_proc = IRB::InputCompletor::CompletionProc
|
188
|
+
end
|
233
189
|
|
234
|
-
|
235
|
-
|
236
|
-
|
237
|
-
|
238
|
-
|
239
|
-
|
240
|
-
|
190
|
+
# Reads the next line from this input method.
|
191
|
+
#
|
192
|
+
# See IO#gets for more information.
|
193
|
+
def gets
|
194
|
+
Readline.input = @stdin
|
195
|
+
Readline.output = @stdout
|
196
|
+
if l = readline(@prompt, false)
|
197
|
+
HISTORY.push(l) if !l.empty?
|
198
|
+
@line[@line_no += 1] = l + "\n"
|
199
|
+
else
|
200
|
+
@eof = true
|
201
|
+
l
|
241
202
|
end
|
203
|
+
end
|
242
204
|
|
243
|
-
|
244
|
-
|
245
|
-
|
246
|
-
|
205
|
+
# Whether the end of this input method has been reached, returns +true+
|
206
|
+
# if there is no more data to read.
|
207
|
+
#
|
208
|
+
# See IO#eof? for more information.
|
209
|
+
def eof?
|
210
|
+
@eof
|
211
|
+
end
|
247
212
|
|
248
|
-
|
249
|
-
|
250
|
-
|
251
|
-
|
252
|
-
|
253
|
-
|
254
|
-
|
255
|
-
end
|
213
|
+
# For debug message
|
214
|
+
def inspect
|
215
|
+
readline_impl = (defined?(Reline) && Readline == Reline) ? 'Reline' : 'ext/readline'
|
216
|
+
str = "ReadlineInputMethod with #{readline_impl} #{Readline::VERSION}"
|
217
|
+
inputrc_path = File.expand_path(ENV['INPUTRC'] || '~/.inputrc')
|
218
|
+
str += " and #{inputrc_path}" if File.exist?(inputrc_path)
|
219
|
+
str
|
256
220
|
end
|
257
221
|
end
|
258
222
|
|
259
|
-
class RelineInputMethod <
|
260
|
-
|
261
|
-
|
223
|
+
class RelineInputMethod < StdioInputMethod
|
224
|
+
HISTORY = Reline::HISTORY
|
225
|
+
include HistorySavingAbility
|
262
226
|
# Creates a new input method object using Reline
|
263
227
|
def initialize
|
264
228
|
IRB.__send__(:set_encoding, Reline.encoding_system_needs.name, override: false)
|
229
|
+
|
265
230
|
super
|
266
231
|
|
267
|
-
@line_no = 0
|
268
|
-
@line = []
|
269
232
|
@eof = false
|
270
233
|
|
271
|
-
|
272
|
-
@stdout = ::IO.open(STDOUT.to_i, 'w', :external_encoding => IRB.conf[:LC_MESSAGES].encoding, :internal_encoding => "-")
|
273
|
-
|
274
|
-
if Reline.respond_to?("basic_word_break_characters=")
|
275
|
-
Reline.basic_word_break_characters = IRB::InputCompletor::BASIC_WORD_BREAK_CHARACTERS
|
276
|
-
end
|
234
|
+
Reline.basic_word_break_characters = IRB::InputCompletor::BASIC_WORD_BREAK_CHARACTERS
|
277
235
|
Reline.completion_append_character = nil
|
278
236
|
Reline.completer_quote_characters = ''
|
279
237
|
Reline.completion_proc = IRB::InputCompletor::CompletionProc
|
@@ -399,11 +357,13 @@ module IRB
|
|
399
357
|
formatter = RDoc::Markup::ToAnsi.new
|
400
358
|
formatter.width = width
|
401
359
|
dialog.trap_key = alt_d
|
402
|
-
|
360
|
+
mod_key = RUBY_PLATFORM.match?(/darwin/) ? "Option" : "Alt"
|
361
|
+
message = "Press #{mod_key}+d to read the full document"
|
403
362
|
contents = [message] + doc.accept(formatter).split("\n")
|
363
|
+
contents = contents.take(preferred_dialog_height)
|
404
364
|
|
405
365
|
y = cursor_pos_to_render.y
|
406
|
-
DialogRenderInfo.new(pos: Reline::CursorPos.new(x, y), contents: contents, width: width, bg_color: '49')
|
366
|
+
Reline::DialogRenderInfo.new(pos: Reline::CursorPos.new(x, y), contents: contents, width: width, bg_color: '49')
|
407
367
|
}
|
408
368
|
|
409
369
|
# Reads the next line from this input method.
|
@@ -414,8 +374,8 @@ module IRB
|
|
414
374
|
Reline.output = @stdout
|
415
375
|
Reline.prompt_proc = @prompt_proc
|
416
376
|
Reline.auto_indent_proc = @auto_indent_proc if @auto_indent_proc
|
417
|
-
if l = readmultiline(@prompt, false, &@check_termination_proc)
|
418
|
-
HISTORY.push(l) if !l.empty?
|
377
|
+
if l = Reline.readmultiline(@prompt, false, &@check_termination_proc)
|
378
|
+
Reline::HISTORY.push(l) if !l.empty?
|
419
379
|
@line[@line_no += 1] = l + "\n"
|
420
380
|
else
|
421
381
|
@eof = true
|
@@ -431,37 +391,11 @@ module IRB
|
|
431
391
|
@eof
|
432
392
|
end
|
433
393
|
|
434
|
-
# Whether this input method is still readable when there is no more data to
|
435
|
-
# read.
|
436
|
-
#
|
437
|
-
# See IO#eof for more information.
|
438
|
-
def readable_after_eof?
|
439
|
-
true
|
440
|
-
end
|
441
|
-
|
442
|
-
# Returns the current line number for #io.
|
443
|
-
#
|
444
|
-
# #line counts the number of times #gets is called.
|
445
|
-
#
|
446
|
-
# See IO#lineno for more information.
|
447
|
-
def line(line_no)
|
448
|
-
@line[line_no]
|
449
|
-
end
|
450
|
-
|
451
|
-
# The external encoding for standard input.
|
452
|
-
def encoding
|
453
|
-
@stdin.external_encoding
|
454
|
-
end
|
455
|
-
|
456
394
|
# For debug message
|
457
395
|
def inspect
|
458
396
|
config = Reline::Config.new
|
459
397
|
str = "RelineInputMethod with Reline #{Reline::VERSION}"
|
460
|
-
|
461
|
-
inputrc_path = File.expand_path(config.inputrc_path)
|
462
|
-
else
|
463
|
-
inputrc_path = File.expand_path(ENV['INPUTRC'] || '~/.inputrc')
|
464
|
-
end
|
398
|
+
inputrc_path = File.expand_path(config.inputrc_path)
|
465
399
|
str += " and #{inputrc_path}" if File.exist?(inputrc_path)
|
466
400
|
str
|
467
401
|
end
|