irb 1.1.1 → 1.2.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.
@@ -8,6 +8,7 @@
8
8
  #
9
9
 
10
10
  require "readline"
11
+ autoload :RDoc, "rdoc"
11
12
 
12
13
  module IRB
13
14
  module InputCompletor # :nodoc:
@@ -35,9 +36,13 @@ module IRB
35
36
  yield
36
37
  ]
37
38
 
39
+ BASIC_WORD_BREAK_CHARACTERS = " \t\n`><=;|&{("
40
+
38
41
  CompletionProc = proc { |input|
39
- bind = IRB.conf[:MAIN_CONTEXT].workspace.binding
42
+ retrieve_completion_data(input).compact.map{ |i| i.encode(Encoding.default_external) }
43
+ }
40
44
 
45
+ def self.retrieve_completion_data(input, bind: IRB.conf[:MAIN_CONTEXT].workspace.binding, doc_namespace: false)
41
46
  case input
42
47
  when /^((["'`]).*\2)\.([^.]*)$/
43
48
  # String
@@ -45,7 +50,11 @@ module IRB
45
50
  message = Regexp.quote($3)
46
51
 
47
52
  candidates = String.instance_methods.collect{|m| m.to_s}
48
- select_message(receiver, message, candidates)
53
+ if doc_namespace
54
+ "String.#{message}"
55
+ else
56
+ select_message(receiver, message, candidates)
57
+ end
49
58
 
50
59
  when /^(\/[^\/]*\/)\.([^.]*)$/
51
60
  # Regexp
@@ -53,7 +62,11 @@ module IRB
53
62
  message = Regexp.quote($2)
54
63
 
55
64
  candidates = Regexp.instance_methods.collect{|m| m.to_s}
56
- select_message(receiver, message, candidates)
65
+ if doc_namespace
66
+ "Regexp.#{message}"
67
+ else
68
+ select_message(receiver, message, candidates)
69
+ end
57
70
 
58
71
  when /^([^\]]*\])\.([^.]*)$/
59
72
  # Array
@@ -61,19 +74,28 @@ module IRB
61
74
  message = Regexp.quote($2)
62
75
 
63
76
  candidates = Array.instance_methods.collect{|m| m.to_s}
64
- select_message(receiver, message, candidates)
77
+ if doc_namespace
78
+ "Array.#{message}"
79
+ else
80
+ select_message(receiver, message, candidates)
81
+ end
65
82
 
66
83
  when /^([^\}]*\})\.([^.]*)$/
67
84
  # Proc or Hash
68
85
  receiver = $1
69
86
  message = Regexp.quote($2)
70
87
 
71
- candidates = Proc.instance_methods.collect{|m| m.to_s}
72
- candidates |= Hash.instance_methods.collect{|m| m.to_s}
73
- select_message(receiver, message, candidates)
88
+ proc_candidates = Proc.instance_methods.collect{|m| m.to_s}
89
+ hash_candidates = Hash.instance_methods.collect{|m| m.to_s}
90
+ if doc_namespace
91
+ ["Proc.#{message}", "Hash.#{message}"]
92
+ else
93
+ select_message(receiver, message, proc_candidates | hash_candidates)
94
+ end
74
95
 
75
96
  when /^(:[^:.]*)$/
76
97
  # Symbol
98
+ return nil if doc_namespace
77
99
  if Symbol.respond_to?(:all_symbols)
78
100
  sym = $1
79
101
  candidates = Symbol.all_symbols.collect{|s| ":" + s.id2name}
@@ -86,7 +108,11 @@ module IRB
86
108
  # Absolute Constant or class methods
87
109
  receiver = $1
88
110
  candidates = Object.constants.collect{|m| m.to_s}
89
- candidates.grep(/^#{receiver}/).collect{|e| "::" + e}
111
+ if doc_namespace
112
+ candidates.find { |i| i == receiver }
113
+ else
114
+ candidates.grep(/^#{receiver}/).collect{|e| "::" + e}
115
+ end
90
116
 
91
117
  when /^([A-Z].*)::([^:.]*)$/
92
118
  # Constant or class methods
@@ -98,7 +124,11 @@ module IRB
98
124
  rescue Exception
99
125
  candidates = []
100
126
  end
101
- select_message(receiver, message, candidates, "::")
127
+ if doc_namespace
128
+ "#{receiver}::#{message}"
129
+ else
130
+ select_message(receiver, message, candidates, "::")
131
+ end
102
132
 
103
133
  when /^(:[^:.]+)(\.|::)([^.]*)$/
104
134
  # Symbol
@@ -107,20 +137,33 @@ module IRB
107
137
  message = Regexp.quote($3)
108
138
 
109
139
  candidates = Symbol.instance_methods.collect{|m| m.to_s}
110
- select_message(receiver, message, candidates, sep)
140
+ if doc_namespace
141
+ "Symbol.#{message}"
142
+ else
143
+ select_message(receiver, message, candidates, sep)
144
+ end
111
145
 
112
- when /^(-?(0[dbo])?[0-9_]+(\.[0-9_]+)?([eE]-?[0-9]+)?)(\.|::)([^.]*)$/
146
+ when /^(?<num>-?(0[dbo])?[0-9_]+(\.[0-9_]+)?(([eE][+-]?[0-9]+)?i?|r)?)(?<sep>\.|::)(?<mes>[^.]*)$/
113
147
  # Numeric
114
- receiver = $1
115
- sep = $5
116
- message = Regexp.quote($6)
148
+ receiver = $~[:num]
149
+ sep = $~[:sep]
150
+ message = Regexp.quote($~[:mes])
117
151
 
118
152
  begin
119
- candidates = eval(receiver, bind).methods.collect{|m| m.to_s}
153
+ instance = eval(receiver, bind)
154
+ if doc_namespace
155
+ "#{instance.class.name}.#{message}"
156
+ else
157
+ candidates = instance.methods.collect{|m| m.to_s}
158
+ select_message(receiver, message, candidates, sep)
159
+ end
120
160
  rescue Exception
121
- candidates = []
161
+ if doc_namespace
162
+ nil
163
+ else
164
+ candidates = []
165
+ end
122
166
  end
123
- select_message(receiver, message, candidates, sep)
124
167
 
125
168
  when /^(-?0x[0-9a-fA-F_]+)(\.|::)([^.]*)$/
126
169
  # Numeric(0xFFFF)
@@ -129,16 +172,30 @@ module IRB
129
172
  message = Regexp.quote($3)
130
173
 
131
174
  begin
132
- candidates = eval(receiver, bind).methods.collect{|m| m.to_s}
175
+ instance = eval(receiver, bind)
176
+ if doc_namespace
177
+ "#{instance.class.name}.#{message}"
178
+ else
179
+ candidates = instance.methods.collect{|m| m.to_s}
180
+ select_message(receiver, message, candidates, sep)
181
+ end
133
182
  rescue Exception
134
- candidates = []
183
+ if doc_namespace
184
+ nil
185
+ else
186
+ candidates = []
187
+ end
135
188
  end
136
- select_message(receiver, message, candidates, sep)
137
189
 
138
190
  when /^(\$[^.]*)$/
139
191
  # global var
140
- regmessage = Regexp.new(Regexp.quote($1))
141
- candidates = global_variables.collect{|m| m.to_s}.grep(regmessage)
192
+ gvar = $1
193
+ all_gvars = global_variables.collect{|m| m.to_s}
194
+ if doc_namespace
195
+ all_gvars.find{ |i| i == gvar }
196
+ else
197
+ all_gvars.grep(Regexp.new(Regexp.quote(gvar)))
198
+ end
142
199
 
143
200
  when /^([^."].*)(\.|::)([^.]*)$/
144
201
  # variable.func or func.func
@@ -146,7 +203,7 @@ module IRB
146
203
  sep = $2
147
204
  message = Regexp.quote($3)
148
205
 
149
- gv = eval("global_variables", bind).collect{|m| m.to_s}
206
+ gv = eval("global_variables", bind).collect{|m| m.to_s}.append("true", "false", "nil")
150
207
  lv = eval("local_variables", bind).collect{|m| m.to_s}
151
208
  iv = eval("instance_variables", bind).collect{|m| m.to_s}
152
209
  cv = eval("self.class.constants", bind).collect{|m| m.to_s}
@@ -177,7 +234,11 @@ module IRB
177
234
  candidates.sort!
178
235
  candidates.uniq!
179
236
  end
180
- select_message(receiver, message, candidates, sep)
237
+ if doc_namespace
238
+ "#{rec.class.name}#{sep}#{candidates.find{ |i| i == message }}"
239
+ else
240
+ select_message(receiver, message, candidates, sep)
241
+ end
181
242
 
182
243
  when /^\.([^.]*)$/
183
244
  # unknown(maybe String)
@@ -186,12 +247,50 @@ module IRB
186
247
  message = Regexp.quote($1)
187
248
 
188
249
  candidates = String.instance_methods(true).collect{|m| m.to_s}
189
- select_message(receiver, message, candidates)
250
+ if doc_namespace
251
+ "String.#{candidates.find{ |i| i == message }}"
252
+ else
253
+ select_message(receiver, message, candidates)
254
+ end
190
255
 
191
256
  else
192
257
  candidates = eval("methods | private_methods | local_variables | instance_variables | self.class.constants", bind).collect{|m| m.to_s}
258
+ conditions |= ReservedWords
193
259
 
194
- (candidates|ReservedWords).grep(/^#{Regexp.quote(input)}/)
260
+ if doc_namespace
261
+ candidates.find{ |i| i == input }
262
+ else
263
+ candidates.grep(/^#{Regexp.quote(input)}/)
264
+ end
265
+ end
266
+ end
267
+
268
+ PerfectMatchedProc = ->(matched) {
269
+ RDocRIDriver ||= RDoc::RI::Driver.new
270
+ if matched =~ /\A(?:::)?RubyVM/ and not ENV['RUBY_YES_I_AM_NOT_A_NORMAL_USER']
271
+ File.open(File.join(__dir__, 'ruby_logo.aa')) do |f|
272
+ RDocRIDriver.page do |io|
273
+ IO.copy_stream(f, io)
274
+ end
275
+ end
276
+ return
277
+ end
278
+ namespace = retrieve_completion_data(matched, doc_namespace: true)
279
+ return unless matched
280
+ if namespace.is_a?(Array)
281
+ out = RDoc::Markup::Document.new
282
+ namespace.each do |m|
283
+ begin
284
+ RDocRIDriver.add_method(out, m)
285
+ rescue RDoc::RI::Driver::NotFoundError
286
+ end
287
+ end
288
+ RDocRIDriver.display(out)
289
+ else
290
+ begin
291
+ RDocRIDriver.display_names([namespace])
292
+ rescue RDoc::RI::Driver::NotFoundError
293
+ end
195
294
  end
196
295
  }
197
296
 
@@ -225,7 +324,7 @@ module IRB
225
324
  end
226
325
  end
227
326
 
228
- %i(IRB SLex RubyLex RubyToken).each do |sym|
327
+ %i(IRB RubyLex).each do |sym|
229
328
  next unless Object.const_defined?(sym)
230
329
  scanner.call(Object.const_get(sym))
231
330
  end
@@ -236,9 +335,3 @@ module IRB
236
335
  end
237
336
  end
238
337
  end
239
-
240
- if Readline.respond_to?("basic_word_break_characters=")
241
- Readline.basic_word_break_characters= " \t\n`><=;|&{("
242
- end
243
- Readline.completion_append_character = nil
244
- Readline.completion_proc = IRB::InputCompletor::CompletionProc
@@ -22,10 +22,10 @@ module IRB
22
22
  #
23
23
  # The optional +input_method+ argument:
24
24
  #
25
- # +nil+:: uses stdin or Readline
25
+ # +nil+:: uses stdin or Reidline or Readline
26
26
  # +String+:: uses a File
27
27
  # +other+:: uses this as InputMethod
28
- def initialize(irb, workspace = nil, input_method = nil, output_method = nil)
28
+ def initialize(irb, workspace = nil, input_method = nil)
29
29
  @irb = irb
30
30
  if workspace
31
31
  @workspace = workspace
@@ -39,7 +39,21 @@ module IRB
39
39
  @rc = IRB.conf[:RC]
40
40
  @load_modules = IRB.conf[:LOAD_MODULES]
41
41
 
42
- @use_readline = IRB.conf[:USE_READLINE]
42
+ if IRB.conf.has_key?(:USE_SINGLELINE)
43
+ @use_singleline = IRB.conf[:USE_SINGLELINE]
44
+ elsif IRB.conf.has_key?(:USE_READLINE) # backward compatibility
45
+ @use_singleline = IRB.conf[:USE_READLINE]
46
+ else
47
+ @use_singleline = nil
48
+ end
49
+ if IRB.conf.has_key?(:USE_MULTILINE)
50
+ @use_multiline = IRB.conf[:USE_MULTILINE]
51
+ elsif IRB.conf.has_key?(:USE_REIDLINE) # backward compatibility
52
+ @use_multiline = IRB.conf[:USE_REIDLINE]
53
+ else
54
+ @use_multiline = nil
55
+ end
56
+ @use_colorize = IRB.conf[:USE_COLORIZE]
43
57
  @verbose = IRB.conf[:VERBOSE]
44
58
  @io = nil
45
59
 
@@ -64,23 +78,48 @@ module IRB
64
78
 
65
79
  case input_method
66
80
  when nil
67
- case use_readline?
81
+ @io = nil
82
+ case use_multiline?
68
83
  when nil
69
- if (defined?(ReadlineInputMethod) && STDIN.tty? &&
70
- IRB.conf[:PROMPT_MODE] != :INF_RUBY)
71
- @io = ReadlineInputMethod.new
84
+ if STDIN.tty? && IRB.conf[:PROMPT_MODE] != :INF_RUBY && !use_singleline?
85
+ # Both of multiline mode and singleline mode aren't specified.
86
+ puts <<~EOM
87
+ This version of IRB is drastically different from the previous version.
88
+ If you hit any issues, you can use "irb --legacy" to run the old version.
89
+ If you want to just erase this message, please use "irb --multiline" or
90
+ add `IRB.conf[:USE_MULTILINE] = true` to your ~/.irbrc file.
91
+ EOM
92
+ @io = ReidlineInputMethod.new
72
93
  else
73
- @io = StdioInputMethod.new
94
+ @io = nil
74
95
  end
75
96
  when false
76
- @io = StdioInputMethod.new
97
+ @io = nil
77
98
  when true
78
- if defined?(ReadlineInputMethod)
79
- @io = ReadlineInputMethod.new
99
+ @io = ReidlineInputMethod.new
100
+ end
101
+ unless @io
102
+ case use_singleline?
103
+ when nil
104
+ if (defined?(ReadlineInputMethod) && STDIN.tty? &&
105
+ IRB.conf[:PROMPT_MODE] != :INF_RUBY)
106
+ @io = ReadlineInputMethod.new
107
+ else
108
+ @io = nil
109
+ end
110
+ when false
111
+ @io = nil
112
+ when true
113
+ if defined?(ReadlineInputMethod)
114
+ @io = ReadlineInputMethod.new
115
+ else
116
+ @io = nil
117
+ end
80
118
  else
81
- @io = StdioInputMethod.new
119
+ @io = nil
82
120
  end
83
121
  end
122
+ @io = StdioInputMethod.new unless @io
84
123
 
85
124
  when String
86
125
  @io = FileInputMethod.new(input_method)
@@ -91,17 +130,15 @@ module IRB
91
130
  end
92
131
  self.save_history = IRB.conf[:SAVE_HISTORY] if IRB.conf[:SAVE_HISTORY]
93
132
 
94
- if output_method
95
- @output_method = output_method
96
- else
97
- @output_method = StdioOutputMethod.new
98
- end
99
-
100
133
  @echo = IRB.conf[:ECHO]
101
134
  if @echo.nil?
102
135
  @echo = true
103
136
  end
104
- self.debug_level = IRB.conf[:DEBUG_LEVEL]
137
+
138
+ @echo_on_assignment = IRB.conf[:ECHO_ON_ASSIGNMENT]
139
+ if @echo_on_assignment.nil?
140
+ @echo_on_assignment = false
141
+ end
105
142
  end
106
143
 
107
144
  # The top-level workspace, see WorkSpace#main
@@ -117,9 +154,9 @@ module IRB
117
154
  attr_reader :thread
118
155
  # The current input method
119
156
  #
120
- # Can be either StdioInputMethod, ReadlineInputMethod, FileInputMethod or
121
- # other specified when the context is created. See ::new for more
122
- # information on +input_method+.
157
+ # Can be either StdioInputMethod, ReadlineInputMethod,
158
+ # ReidlineInputMethod, FileInputMethod or other specified when the
159
+ # context is created. See ::new for more # information on +input_method+.
123
160
  attr_accessor :io
124
161
 
125
162
  # Current irb session
@@ -137,12 +174,18 @@ module IRB
137
174
  # +input_method+ passed to Context.new
138
175
  attr_accessor :irb_path
139
176
 
140
- # Whether +Readline+ is enabled or not.
177
+ # Whether multiline editor mode is enabled or not.
178
+ #
179
+ # A copy of the default <code>IRB.conf[:USE_MULTILINE]</code>
180
+ attr_reader :use_multiline
181
+ # Whether singleline editor mode is enabled or not.
141
182
  #
142
- # A copy of the default <code>IRB.conf[:USE_READLINE]</code>
183
+ # A copy of the default <code>IRB.conf[:USE_SINGLELINE]</code>
184
+ attr_reader :use_singleline
185
+ # Whether colorization is enabled or not.
143
186
  #
144
- # See #use_readline= for more information.
145
- attr_reader :use_readline
187
+ # A copy of the default <code>IRB.conf[:USE_COLORIZE]</code>
188
+ attr_reader :use_colorize
146
189
  # A copy of the default <code>IRB.conf[:INSPECT_MODE]</code>
147
190
  attr_reader :inspect_mode
148
191
 
@@ -165,17 +208,17 @@ module IRB
165
208
  # Can be either the default <code>IRB.conf[:AUTO_INDENT]</code>, or the
166
209
  # mode set by #prompt_mode=
167
210
  #
168
- # To enable auto-indentation in irb:
211
+ # To disable auto-indentation in irb:
169
212
  #
170
- # IRB.conf[:AUTO_INDENT] = true
213
+ # IRB.conf[:AUTO_INDENT] = false
171
214
  #
172
215
  # or
173
216
  #
174
- # irb_context.auto_indent_mode = true
217
+ # irb_context.auto_indent_mode = false
175
218
  #
176
219
  # or
177
220
  #
178
- # IRB.CurrentContext.auto_indent_mode = true
221
+ # IRB.CurrentContext.auto_indent_mode = false
179
222
  #
180
223
  # See IRB@Configuration for more information.
181
224
  attr_accessor :auto_indent_mode
@@ -207,14 +250,19 @@ module IRB
207
250
  # puts "omg"
208
251
  # # omg
209
252
  attr_accessor :echo
253
+ # Whether to echo for assignment expressions
254
+ #
255
+ # Uses IRB.conf[:ECHO_ON_ASSIGNMENT] if available, or defaults to +false+.
256
+ #
257
+ # a = "omg"
258
+ # IRB.CurrentContext.echo_on_assignment = true
259
+ # a = "omg"
260
+ # #=> omg
261
+ attr_accessor :echo_on_assignment
210
262
  # Whether verbose messages are displayed or not.
211
263
  #
212
264
  # A copy of the default <code>IRB.conf[:VERBOSE]</code>
213
265
  attr_accessor :verbose
214
- # The debug level of irb
215
- #
216
- # See #debug_level= for more information.
217
- attr_reader :debug_level
218
266
 
219
267
  # The limit of backtrace lines displayed as top +n+ and tail +n+.
220
268
  #
@@ -225,18 +273,33 @@ module IRB
225
273
  # See IRB@Command+line+options for more command line options.
226
274
  attr_accessor :back_trace_limit
227
275
 
228
- # Alias for #use_readline
229
- alias use_readline? use_readline
276
+ # Alias for #use_multiline
277
+ alias use_multiline? use_multiline
278
+ # Alias for #use_singleline
279
+ alias use_singleline? use_singleline
280
+ # backward compatibility
281
+ alias use_reidline use_multiline
282
+ # backward compatibility
283
+ alias use_reidline? use_multiline
284
+ # backward compatibility
285
+ alias use_readline use_singleline
286
+ # backward compatibility
287
+ alias use_readline? use_singleline
288
+ # Alias for #use_colorize
289
+ alias use_colorize? use_colorize
230
290
  # Alias for #rc
231
291
  alias rc? rc
232
292
  alias ignore_sigint? ignore_sigint
233
293
  alias ignore_eof? ignore_eof
234
294
  alias echo? echo
295
+ alias echo_on_assignment? echo_on_assignment
235
296
 
236
297
  # Returns whether messages are displayed or not.
237
298
  def verbose?
238
299
  if @verbose.nil?
239
- if defined?(ReadlineInputMethod) && @io.kind_of?(ReadlineInputMethod)
300
+ if @io.kind_of?(ReidlineInputMethod)
301
+ false
302
+ elsif defined?(ReadlineInputMethod) && @io.kind_of?(ReadlineInputMethod)
240
303
  false
241
304
  elsif !STDIN.tty? or @io.kind_of?(FileInputMethod)
242
305
  true
@@ -249,9 +312,11 @@ module IRB
249
312
  end
250
313
 
251
314
  # Whether #verbose? is +true+, and +input_method+ is either
252
- # StdioInputMethod or ReadlineInputMethod, see #io for more information.
315
+ # StdioInputMethod or ReidlineInputMethod or ReadlineInputMethod, see #io
316
+ # for more information.
253
317
  def prompting?
254
318
  verbose? || (STDIN.tty? && @io.kind_of?(StdioInputMethod) ||
319
+ @io.kind_of?(ReidlineInputMethod) ||
255
320
  (defined?(ReadlineInputMethod) && @io.kind_of?(ReadlineInputMethod)))
256
321
  end
257
322
 
@@ -350,36 +415,11 @@ module IRB
350
415
  @inspect_mode
351
416
  end
352
417
 
353
- # Obsolete method.
354
- #
355
- # Can be set using the +--noreadline+ and +--readline+ command line
356
- # options.
357
- #
358
- # See IRB@Command+line+options for more command line options.
359
- def use_readline=(opt)
360
- print "This method is obsolete."
361
- print "Do nothing."
362
- end
363
-
364
- # Sets the debug level of irb
365
- #
366
- # Can also be set using the +--irb_debug+ command line option.
367
- #
368
- # See IRB@Command+line+options for more command line options.
369
- def debug_level=(value)
370
- @debug_level = value
371
- RubyLex.debug_level = value
372
- end
373
-
374
- # Whether or not debug mode is enabled, see #debug_level=.
375
- def debug?
376
- @debug_level > 0
377
- end
378
-
379
418
  def evaluate(line, line_no, exception: nil) # :nodoc:
380
419
  @line_no = line_no
381
420
  if exception
382
- line = "begin ::Kernel.raise _; rescue _.class; #{line}; end"
421
+ line_no -= 1
422
+ line = "begin ::Kernel.raise _; rescue _.class\n#{line}\n""end"
383
423
  @workspace.local_variable_set(:_, exception)
384
424
  end
385
425
  set_last_value(@workspace.evaluate(self, line, irb_path, line_no))