pry 0.9.3 → 0.9.4pre1
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/CHANGELOG +11 -0
- data/CONTRIBUTORS +11 -0
- data/README.markdown +2 -2
- data/TODO +15 -0
- data/lib/pry.rb +0 -1
- data/lib/pry/command_context.rb +1 -0
- data/lib/pry/command_processor.rb +7 -13
- data/lib/pry/command_set.rb +3 -3
- data/lib/pry/completion.rb +1 -1
- data/lib/pry/default_commands/basic.rb +8 -4
- data/lib/pry/default_commands/context.rb +1 -1
- data/lib/pry/default_commands/documentation.rb +15 -1
- data/lib/pry/default_commands/input.rb +5 -5
- data/lib/pry/default_commands/introspection.rb +3 -38
- data/lib/pry/default_commands/ls.rb +22 -14
- data/lib/pry/default_commands/shell.rb +25 -14
- data/lib/pry/extended_commands/user_command_api.rb +32 -1
- data/lib/pry/helpers/base_helpers.rb +5 -4
- data/lib/pry/helpers/command_helpers.rb +39 -4
- data/lib/pry/helpers/text.rb +10 -10
- data/lib/pry/pry_class.rb +28 -4
- data/lib/pry/pry_instance.rb +34 -16
- data/lib/pry/version.rb +1 -1
- data/test/test_command_processor.rb +8 -87
- data/test/test_command_set.rb +33 -0
- data/test/test_completion.rb +23 -0
- data/test/test_default_commands/test_input.rb +21 -0
- data/test/test_default_commands/test_introspection.rb +1 -1
- data/test/test_pry.rb +1 -1
- data/test/test_pry_history.rb +82 -0
- metadata +10 -5
data/CHANGELOG
CHANGED
@@ -1,3 +1,14 @@
|
|
1
|
+
*/8/2011 version 0.9.4
|
2
|
+
* tempfile should end in .rb (for edit -t)
|
3
|
+
* ls output should not be in array format
|
4
|
+
* fix history saving (should not save all of Readline::HISTORY, but only what changed)
|
5
|
+
* prevent blank lines going to Readline::HISTORY (thanks cirwin!)
|
6
|
+
* ensure that cat --ex emulates the `whereami` format - includes line numbers and formatted the same, etc
|
7
|
+
* fixed bug #200 ( https://github.com/pry/pry/issues/200 )- string interpolation bug (thanks to ryanf)
|
8
|
+
* show-doc and stat now display method visibility (update WIKI)
|
9
|
+
* got rid of warnings caused by stricter ruby 1.9.3 rules
|
10
|
+
* remove interpolation of command names and fix interpolation error messag (update WIKI) (thanks ryanf!)
|
11
|
+
|
1
12
|
*/7/2011 version 0.9.3
|
2
13
|
* cat --ex (cats 5 lines above and below line in file where exception was raised)
|
3
14
|
* edit --ex (edits line in file where exception was raised)
|
data/CONTRIBUTORS
ADDED
@@ -0,0 +1,11 @@
|
|
1
|
+
547 John Mair <jrmair@gmail.com>
|
2
|
+
76 Rob Gleeson <rob@flowof.info>
|
3
|
+
46 Lee Jarvis <lee@jarvis.co>
|
4
|
+
46 Mon ouïe <mon.ouie@gmail.com>
|
5
|
+
18 David Palm <dpalm@elctech.com>
|
6
|
+
13 epitron <chris@ill-logic.com>
|
7
|
+
8 Conrad Irwin <conrad.irwin@gmail.com>
|
8
|
+
6 Ryan Fitzgerald <rwfitzge@gmail.com>
|
9
|
+
2 Eric Christopherson <echristopherson@gmail.com>
|
10
|
+
2 Xavier Shay <xavier@rhnh.net>
|
11
|
+
1 Josh Cheek <josh.cheek@gmail.com>
|
data/README.markdown
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-

|
2
2
|
|
3
3
|
(C) John Mair (banisterfiend) 2011
|
4
4
|
|
@@ -7,7 +7,7 @@ _Get to the code_
|
|
7
7
|
**Note that JRuby is not yet supported in this release, but will be
|
8
8
|
soon.**
|
9
9
|
|
10
|
-
[Skip to the website](http://pry.github.com) <br />
|
10
|
+
[Skip to the website (recommended)](http://pry.github.com) <br />
|
11
11
|
[Skip to the wiki](https://github.com/pry/pry/wiki)
|
12
12
|
|
13
13
|
Pry is a powerful alternative to the standard IRB shell for Ruby. It is
|
data/TODO
CHANGED
@@ -1,3 +1,18 @@
|
|
1
|
+
0.9.4
|
2
|
+
* include method visiblity in show-doc and stat output
|
3
|
+
* tempfile should end in .rb (for edit -t)
|
4
|
+
* ls output should not be in array format
|
5
|
+
* exceptions should allow access to previous items in the backtrace
|
6
|
+
* input should allow multiple objects which are switched to automatically when EOF is reached on the preceding one
|
7
|
+
* pry -r should happen in pry
|
8
|
+
* more plugin-related commands in pry - see installed ones, see activated ones, see available on rubygems
|
9
|
+
* should also allow plugins be explicitly activated as a command line option
|
10
|
+
* should not raise if plugin activation fails (should show warning instead)
|
11
|
+
* more documentation on CommandContext, etc and also command helpers
|
12
|
+
* fix history saving (should not save all of Readline::HISTORY, but only what changed)
|
13
|
+
* prevent blank lines going to Readline::HISTORY
|
14
|
+
* ensure that cat --ex emulates the `whereami` format - includes line numbers and formatted the same, etc
|
15
|
+
|
1
16
|
0.9.3
|
2
17
|
* hist command now excludes last line of input (the command invocation itself)
|
3
18
|
* hist now has `history` alias
|
data/lib/pry.rb
CHANGED
data/lib/pry/command_context.rb
CHANGED
@@ -54,24 +54,17 @@ class Pry
|
|
54
54
|
# @return [Array] The command data and arg string pair
|
55
55
|
def command_matched(val, target)
|
56
56
|
_, cmd_data = commands.commands.find do |name, data|
|
57
|
-
|
58
|
-
prefix = Regexp.escape(Pry.config.command_prefix)
|
57
|
+
prefix = convert_to_regex(Pry.config.command_prefix)
|
59
58
|
prefix = "(?:#{prefix})?" unless data.options[:use_prefix]
|
60
59
|
|
61
60
|
command_regex = /^#{prefix}#{convert_to_regex(name)}(?!\S)/
|
62
61
|
|
63
|
-
if
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
interp_val = interpolate_string(val, target)
|
68
|
-
rescue Exception
|
69
|
-
next
|
62
|
+
if command_regex =~ val
|
63
|
+
if data.options[:interpolate]
|
64
|
+
val.replace(interpolate_string(val, target))
|
65
|
+
command_regex =~ val # re-match with the interpolated string
|
70
66
|
end
|
71
|
-
|
72
|
-
val.replace interp_val if command_regex =~ interp_val
|
73
|
-
else
|
74
|
-
command_regex =~ val
|
67
|
+
true
|
75
68
|
end
|
76
69
|
end
|
77
70
|
|
@@ -128,6 +121,7 @@ class Pry
|
|
128
121
|
context.eval_string = options[:eval_string]
|
129
122
|
context.arg_string = options[:arg_string]
|
130
123
|
context.command_set = commands
|
124
|
+
context._pry_ = @pry_instance
|
131
125
|
|
132
126
|
context.command_processor = self
|
133
127
|
|
data/lib/pry/command_set.rb
CHANGED
@@ -227,11 +227,11 @@ class Pry
|
|
227
227
|
output.puts
|
228
228
|
help_text = heading("Command List: ") + "\n"
|
229
229
|
|
230
|
-
commands.
|
230
|
+
help_text << commands.map do |key, command|
|
231
231
|
if command.description && !command.description.empty?
|
232
|
-
|
232
|
+
"#{command.options[:listing]}".ljust(18) + command.description
|
233
233
|
end
|
234
|
-
end
|
234
|
+
end.compact.sort.join("\n")
|
235
235
|
|
236
236
|
stagger_output(help_text)
|
237
237
|
else
|
data/lib/pry/completion.rb
CHANGED
@@ -8,11 +8,11 @@ class Pry
|
|
8
8
|
end
|
9
9
|
|
10
10
|
command "simple-prompt", "Toggle the simple prompt." do
|
11
|
-
case
|
11
|
+
case _pry_.prompt
|
12
12
|
when Pry::SIMPLE_PROMPT
|
13
|
-
|
13
|
+
_pry_.pop_prompt
|
14
14
|
else
|
15
|
-
|
15
|
+
_pry_.push_prompt Pry::SIMPLE_PROMPT
|
16
16
|
end
|
17
17
|
end
|
18
18
|
|
@@ -24,7 +24,7 @@ class Pry
|
|
24
24
|
next output.puts "Provide a command set name" if command_set.nil?
|
25
25
|
|
26
26
|
set = target.eval(arg_string)
|
27
|
-
|
27
|
+
_pry_.commands.import set
|
28
28
|
end
|
29
29
|
|
30
30
|
command "reload-method", "Reload the source file that contains the specified method" do |meth_name|
|
@@ -44,6 +44,10 @@ class Pry
|
|
44
44
|
end
|
45
45
|
end
|
46
46
|
|
47
|
+
command "req", "Require file(s) and expand their paths." do |*args|
|
48
|
+
args.each { |file_name| load File.expand_path(file_name) }
|
49
|
+
end
|
50
|
+
|
47
51
|
command "reset", "Reset the REPL to a clean state." do
|
48
52
|
output.puts "Pry reset."
|
49
53
|
exec "pry"
|
@@ -67,7 +67,7 @@ class Pry
|
|
67
67
|
alias_command "!!@", "exit-all", ""
|
68
68
|
|
69
69
|
command "exit-program", "End the current program. Aliases: quit-program, !!!" do
|
70
|
-
Pry.
|
70
|
+
Pry.save_history if Pry.config.history.should_save
|
71
71
|
exit
|
72
72
|
end
|
73
73
|
|
@@ -40,8 +40,9 @@ class Pry
|
|
40
40
|
next output.puts("No documentation found.") if doc.empty?
|
41
41
|
doc = process_comment_markup(doc, code_type)
|
42
42
|
output.puts make_header(meth, code_type, doc)
|
43
|
+
output.puts "#{text.bold("visibility: ")} #{method_visibility(meth).to_s}"
|
43
44
|
if meth.respond_to?(:parameters)
|
44
|
-
output.puts "#{text.bold("signature")}
|
45
|
+
output.puts "#{text.bold("signature: ")} #{signature_for(meth)}"
|
45
46
|
output.puts
|
46
47
|
end
|
47
48
|
render_output(opts.flood?, false, doc)
|
@@ -84,6 +85,7 @@ class Pry
|
|
84
85
|
output.puts "--"
|
85
86
|
output.puts "Name: " + meth_name
|
86
87
|
output.puts "Owner: " + (meth.owner.to_s ? meth.owner.to_s : "Unknown")
|
88
|
+
output.puts "Visibility: " + method_visibility(meth).to_s
|
87
89
|
output.puts "Type: " + (meth.is_a?(Method) ? "Bound" : "Unbound")
|
88
90
|
output.puts "Arity: " + meth.arity.to_s
|
89
91
|
|
@@ -156,6 +158,18 @@ class Pry
|
|
156
158
|
end
|
157
159
|
"#{meth.name}(#{param_strings.join(", ")})"
|
158
160
|
end
|
161
|
+
|
162
|
+
def method_visibility(meth)
|
163
|
+
if meth.owner.public_instance_methods.include? meth.name
|
164
|
+
:public
|
165
|
+
elsif meth.owner.protected_instance_methods.include? meth.name
|
166
|
+
:protected
|
167
|
+
elsif meth.owner.private_instance_methods.include? meth.name
|
168
|
+
:private
|
169
|
+
else
|
170
|
+
:none
|
171
|
+
end
|
172
|
+
end
|
159
173
|
end
|
160
174
|
|
161
175
|
end
|
@@ -66,7 +66,7 @@ e.g amend-line puts 'hello again' # no line number modifies immediately preced
|
|
66
66
|
output.puts opt
|
67
67
|
end
|
68
68
|
|
69
|
-
opt.on_noopts {
|
69
|
+
opt.on_noopts { _pry_.input = StringIO.new(arg_string) }
|
70
70
|
end
|
71
71
|
|
72
72
|
if opts.m?
|
@@ -75,13 +75,13 @@ e.g amend-line puts 'hello again' # no line number modifies immediately preced
|
|
75
75
|
output.puts "Invalid method name: #{meth_name}."
|
76
76
|
next
|
77
77
|
end
|
78
|
-
code,
|
78
|
+
code, _ = code_and_code_type_for(meth)
|
79
79
|
next if !code
|
80
80
|
|
81
81
|
range = opts.l? ? one_index_range_or_number(opts[:l]) : (0..-1)
|
82
82
|
range = (0..-2) if opts.o?
|
83
83
|
|
84
|
-
|
84
|
+
_pry_.input = StringIO.new(Array(code.each_line.to_a[range]).join)
|
85
85
|
end
|
86
86
|
|
87
87
|
if opts.f?
|
@@ -91,7 +91,7 @@ e.g amend-line puts 'hello again' # no line number modifies immediately preced
|
|
91
91
|
range = opts.l? ? one_index_range_or_number(opts[:l]) : (0..-1)
|
92
92
|
range = (0..-2) if opts.o?
|
93
93
|
|
94
|
-
|
94
|
+
_pry_.input = StringIO.new(Array(text_array[range]).join)
|
95
95
|
end
|
96
96
|
end
|
97
97
|
|
@@ -164,7 +164,7 @@ e.g amend-line puts 'hello again' # no line number modifies immediately preced
|
|
164
164
|
:as => Range,
|
165
165
|
:unless => :grep do |range|
|
166
166
|
actions = Array(history[range]).join("\n") + "\n"
|
167
|
-
|
167
|
+
_pry_.input = StringIO.new(actions)
|
168
168
|
end
|
169
169
|
|
170
170
|
opt.on "save", "Save history to a file. --save [start..end] output.txt. Pry commands are excluded from saved history.", true, :as => Range
|
@@ -135,7 +135,7 @@ class Pry
|
|
135
135
|
next output.puts "Exception has no associated file." if file_name.nil?
|
136
136
|
next output.puts "Cannot edit exceptions raised in REPL." if Pry.eval_path == file_name
|
137
137
|
elsif opts.t?
|
138
|
-
file_name = Tempfile.new("tmp").tap(&:close).path
|
138
|
+
file_name = Tempfile.new(["tmp", ".rb"]).tap(&:close).path
|
139
139
|
line = 0
|
140
140
|
should_reload = true
|
141
141
|
context = target
|
@@ -150,11 +150,11 @@ class Pry
|
|
150
150
|
|
151
151
|
if opts[:p]
|
152
152
|
silence_warnings do
|
153
|
-
|
153
|
+
_pry_.input = StringIO.new(File.readlines(file_name).join)
|
154
154
|
end
|
155
155
|
elsif should_reload
|
156
156
|
silence_warnings do
|
157
|
-
context.eval(File.read(file_name))
|
157
|
+
context.eval(File.read(file_name), file_name)
|
158
158
|
end
|
159
159
|
end
|
160
160
|
end
|
@@ -207,41 +207,6 @@ class Pry
|
|
207
207
|
end
|
208
208
|
end
|
209
209
|
|
210
|
-
helpers do
|
211
|
-
|
212
|
-
def invoke_editor(file, line)
|
213
|
-
if Pry.editor.respond_to?(:call)
|
214
|
-
editor_invocation = Pry.editor.call(file, line)
|
215
|
-
else
|
216
|
-
editor_invocation = "#{Pry.editor} #{start_line_syntax_for_editor(file, line)}"
|
217
|
-
end
|
218
|
-
|
219
|
-
run ".#{editor_invocation}"
|
220
|
-
end
|
221
|
-
|
222
|
-
def start_line_syntax_for_editor(file_name, line_number)
|
223
|
-
file_name = file_name.gsub(/\//, '\\') if RUBY_PLATFORM =~ /mswin|mingw/
|
224
|
-
|
225
|
-
case Pry.editor
|
226
|
-
when /^[gm]?vi/, /^emacs/, /^nano/, /^pico/, /^gedit/, /^kate/
|
227
|
-
"+#{line_number} #{file_name}"
|
228
|
-
when /^mate/, /^geany/
|
229
|
-
"-l #{line_number} #{file_name}"
|
230
|
-
when /^uedit32/
|
231
|
-
"#{file_name}/#{line_number}"
|
232
|
-
when /^jedit/
|
233
|
-
"#{file_name} +line:#{line_number}"
|
234
|
-
else
|
235
|
-
if RUBY_PLATFORM =~ /mswin|mingw/
|
236
|
-
"#{file_name}"
|
237
|
-
else
|
238
|
-
"+#{line_number} #{file_name}"
|
239
|
-
end
|
240
|
-
end
|
241
|
-
end
|
242
|
-
|
243
|
-
end
|
244
|
-
|
245
210
|
end
|
246
211
|
end
|
247
212
|
end
|
@@ -19,6 +19,23 @@ class Pry
|
|
19
19
|
Object.send("#{visibility}_instance_methods")
|
20
20
|
end
|
21
21
|
end
|
22
|
+
|
23
|
+
def ls_color_map
|
24
|
+
{
|
25
|
+
"local variables" => :bright_red,
|
26
|
+
"instance variables" => :bright_blue,
|
27
|
+
"class variables" => :blue,
|
28
|
+
"global variables" => :bright_magenta,
|
29
|
+
"just singleton methods" => :green,
|
30
|
+
"public methods" => :green,
|
31
|
+
"private methods" => :green,
|
32
|
+
"protected methods" => :green,
|
33
|
+
"public instance methods" => :bright_green,
|
34
|
+
"private instance methods" => :bright_green,
|
35
|
+
"protected instance methods" => :bright_green,
|
36
|
+
"constants" => :red
|
37
|
+
}
|
38
|
+
end
|
22
39
|
end
|
23
40
|
|
24
41
|
command "ls", "Show the list of vars and methods in the current scope. Type `ls --help` for more info." do |*args|
|
@@ -154,7 +171,7 @@ Shows local and instance variables by default.
|
|
154
171
|
|
155
172
|
info["private methods"] = [Array(target.eval("private_methods(#{options[:s]})")).sort - trim_methods(target, options, :private), i += 1] if (options[:m] && options[:p]) || options[:a]
|
156
173
|
|
157
|
-
info["just singleton methods"] = [Array(target.eval("methods(#{options[:s]})")).sort, i += 1] if (options[:m] && options[:j])
|
174
|
+
info["just singleton methods"] = [Array(target.eval("methods(#{options[:s]})")).sort, i += 1] if (options[:m] && options[:j]) && !options[:a]
|
158
175
|
|
159
176
|
info["public instance methods"] = [Array(target.eval("public_instance_methods(#{options[:s]})")).uniq.sort - trim_methods(target, options, :public), i += 1] if target_self.is_a?(Module) && ((options[:M] && options[:P]) || options[:a])
|
160
177
|
|
@@ -181,11 +198,7 @@ Shows local and instance variables by default.
|
|
181
198
|
if !v.first.empty?
|
182
199
|
text << "#{k}:\n--\n"
|
183
200
|
filtered_list = v.first.grep options[:grep]
|
184
|
-
|
185
|
-
text << CodeRay.scan(Pry.view(filtered_list), :ruby).term + "\n"
|
186
|
-
else
|
187
|
-
text << Pry.view(filtered_list) + "\n"
|
188
|
-
end
|
201
|
+
text << text().bright_green(filtered_list.join(" "))
|
189
202
|
text << "\n\n"
|
190
203
|
end
|
191
204
|
end
|
@@ -198,14 +211,9 @@ Shows local and instance variables by default.
|
|
198
211
|
|
199
212
|
# plain
|
200
213
|
else
|
201
|
-
list = info.
|
202
|
-
list = list.
|
203
|
-
|
204
|
-
if Pry.color
|
205
|
-
text << CodeRay.scan(list.inspect, :ruby).term + "\n"
|
206
|
-
else
|
207
|
-
text << list.inspect + "\n"
|
208
|
-
end
|
214
|
+
list = info.sort_by { |k, v| v.last }.map { |k, v| [k, [v.first.grep(options[:grep])], v.last] }
|
215
|
+
list = list.each { |k, v| text << text().send(ls_color_map[k], v.first.join(" ")); text << " " }
|
216
|
+
|
209
217
|
if !options[:f]
|
210
218
|
stagger_output(text)
|
211
219
|
else
|
@@ -20,15 +20,15 @@ class Pry
|
|
20
20
|
end
|
21
21
|
|
22
22
|
command "shell-mode", "Toggle shell mode. Bring in pwd prompt and file completion." do
|
23
|
-
case
|
23
|
+
case _pry_.prompt
|
24
24
|
when Pry::SHELL_PROMPT
|
25
|
-
|
26
|
-
|
25
|
+
_pry_.pop_prompt
|
26
|
+
_pry_.custom_completions = Pry::DEFAULT_CUSTOM_COMPLETIONS
|
27
27
|
else
|
28
|
-
|
29
|
-
|
28
|
+
_pry_.push_prompt Pry::SHELL_PROMPT
|
29
|
+
_pry_.custom_completions = Pry::FILE_COMPLETIONS
|
30
30
|
Readline.completion_proc = Pry::InputCompleter.build_completion_proc target,
|
31
|
-
|
31
|
+
_pry_.instance_eval(&Pry::FILE_COMPLETIONS)
|
32
32
|
end
|
33
33
|
end
|
34
34
|
|
@@ -48,7 +48,7 @@ class Pry
|
|
48
48
|
end_line = line - 1
|
49
49
|
end
|
50
50
|
|
51
|
-
opt.on :ex, "Show a window of N lines
|
51
|
+
opt.on :ex, "Show a window of N lines either side of the last exception (defaults to 5).", :optional => true, :as => Integer do |window_size|
|
52
52
|
window_size ||= 5
|
53
53
|
ex = Pry.last_exception
|
54
54
|
next if !ex
|
@@ -80,27 +80,38 @@ class Pry
|
|
80
80
|
next
|
81
81
|
end
|
82
82
|
|
83
|
-
contents,
|
83
|
+
contents, _, _ = read_between_the_lines(file_name, start_line, end_line)
|
84
|
+
contents = syntax_highlight_by_file_type_or_specified(contents, file_name, opts[:type])
|
85
|
+
|
86
|
+
if opts.l?
|
87
|
+
contents = text.with_line_numbers contents, start_line + 1
|
88
|
+
end
|
84
89
|
|
85
90
|
# add the arrow pointing to line that caused the exception
|
86
91
|
if opts.ex?
|
92
|
+
contents = text.with_line_numbers contents, start_line + 1, :bright_red
|
93
|
+
|
87
94
|
contents = contents.lines.each_with_index.map do |line, idx|
|
88
95
|
l = idx + start_line
|
89
96
|
if l == (Pry.last_exception.line - 1)
|
90
|
-
"
|
97
|
+
" =>#{line}"
|
91
98
|
else
|
92
99
|
" #{line}"
|
93
100
|
end
|
94
101
|
end.join
|
95
|
-
end
|
96
102
|
|
97
|
-
|
98
|
-
|
103
|
+
# header for exceptions
|
104
|
+
output.puts "\n#{Pry::Helpers::Text.bold('Exception:')}: #{Pry.last_exception.class}: #{Pry.last_exception.message}"
|
105
|
+
output.puts "#{Pry::Helpers::Text.bold('From:')} #{file_name} @ line #{Pry.last_exception.line}\n\n"
|
99
106
|
end
|
100
107
|
|
101
108
|
set_file_and_dir_locals(file_name)
|
102
|
-
|
103
|
-
|
109
|
+
|
110
|
+
if opts.f?
|
111
|
+
output.puts contents
|
112
|
+
else
|
113
|
+
stagger_output(contents)
|
114
|
+
end
|
104
115
|
end
|
105
116
|
end
|
106
117
|
|
@@ -7,7 +7,7 @@ class Pry
|
|
7
7
|
next output.puts("Provide an arg!") if arg.nil?
|
8
8
|
|
9
9
|
prime_string = "command #{arg_string}\n"
|
10
|
-
command_string =
|
10
|
+
command_string = _pry_.r(target, prime_string)
|
11
11
|
|
12
12
|
eval_string.replace <<-HERE
|
13
13
|
_pry_.commands.instance_eval do
|
@@ -17,6 +17,37 @@ class Pry
|
|
17
17
|
|
18
18
|
end
|
19
19
|
|
20
|
+
command "reload-command", "Reload a command. reload-command CMD_NAME CMD_SET" do |command_name, set_name|
|
21
|
+
next output.puts "Must provide command name" if command_name.nil?
|
22
|
+
next output.puts "Must provide command set name" if set_name.nil?
|
23
|
+
|
24
|
+
cmd = Pry.config.commands.commands[command_name]
|
25
|
+
file_name = cmd.block.source_location.first
|
26
|
+
|
27
|
+
silence_warnings do
|
28
|
+
load file_name
|
29
|
+
end
|
30
|
+
Pry.config.commands.import target.eval(set_name)
|
31
|
+
_pry_.commands.import target.eval(set_name)
|
32
|
+
set_file_and_dir_locals(file_name)
|
33
|
+
end
|
34
|
+
|
35
|
+
command "edit-command", "Edit a command. edit-command CMD_NAME CMD_SET" do |command_name, set_name|
|
36
|
+
next output.puts "Must provide command name" if command_name.nil?
|
37
|
+
next output.puts "Must provide a command set name" if set_name.nil?
|
38
|
+
|
39
|
+
cmd = Pry.config.commands.commands[command_name]
|
40
|
+
file_name = cmd.block.source_location.first
|
41
|
+
|
42
|
+
invoke_editor(*cmd.block.source_location)
|
43
|
+
silence_warnings do
|
44
|
+
load file_name
|
45
|
+
end
|
46
|
+
Pry.config.commands.import target.eval(set_name)
|
47
|
+
_pry_.commands.import target.eval(set_name)
|
48
|
+
set_file_and_dir_locals(file_name)
|
49
|
+
end
|
50
|
+
|
20
51
|
end
|
21
52
|
end
|
22
53
|
end
|
@@ -2,6 +2,7 @@ class Pry
|
|
2
2
|
module Helpers
|
3
3
|
|
4
4
|
module BaseHelpers
|
5
|
+
|
5
6
|
module_function
|
6
7
|
|
7
8
|
def silence_warnings
|
@@ -72,7 +73,7 @@ class Pry
|
|
72
73
|
end
|
73
74
|
|
74
75
|
def highlight(string, regexp, highlight_color=:bright_yellow)
|
75
|
-
|
76
|
+
string.gsub(regexp) { |match| "<#{highlight_color}>#{match}</#{highlight_color}>" }
|
76
77
|
end
|
77
78
|
|
78
79
|
# formatting
|
@@ -86,7 +87,7 @@ class Pry
|
|
86
87
|
end
|
87
88
|
|
88
89
|
# a simple pager for systems without `less`. A la windows.
|
89
|
-
def simple_pager(text)
|
90
|
+
def simple_pager(text, output=output())
|
90
91
|
text_array = text.lines.to_a
|
91
92
|
text_array.each_slice(page_size) do |chunk|
|
92
93
|
output.puts chunk.join
|
@@ -109,12 +110,12 @@ class Pry
|
|
109
110
|
|
110
111
|
# FIXME! Another JRuby hack
|
111
112
|
if Object.const_defined?(:RUBY_ENGINE) && RUBY_ENGINE =~ /jruby/
|
112
|
-
simple_pager(text)
|
113
|
+
simple_pager(text, output)
|
113
114
|
else
|
114
115
|
lesspipe { |less| less.puts text }
|
115
116
|
end
|
116
117
|
rescue Errno::ENOENT
|
117
|
-
simple_pager(text)
|
118
|
+
simple_pager(text, output)
|
118
119
|
rescue Errno::EPIPE
|
119
120
|
end
|
120
121
|
|
@@ -15,9 +15,9 @@ class Pry
|
|
15
15
|
end
|
16
16
|
|
17
17
|
# if start_line is not false then add line numbers starting with start_line
|
18
|
-
def render_output(should_flood, start_line, text)
|
18
|
+
def render_output(should_flood, start_line, text, color=:blue)
|
19
19
|
if start_line
|
20
|
-
text = Pry::Helpers::Text.with_line_numbers text, start_line
|
20
|
+
text = Pry::Helpers::Text.with_line_numbers text, start_line, color
|
21
21
|
end
|
22
22
|
|
23
23
|
if should_flood
|
@@ -255,7 +255,11 @@ class Pry
|
|
255
255
|
end
|
256
256
|
|
257
257
|
language_detected = file_type if file_type
|
258
|
-
|
258
|
+
if Pry.color
|
259
|
+
CodeRay.scan(contents, language_detected).term
|
260
|
+
else
|
261
|
+
contents
|
262
|
+
end
|
259
263
|
end
|
260
264
|
|
261
265
|
# convert negative line numbers to positive by wrapping around
|
@@ -286,7 +290,7 @@ class Pry
|
|
286
290
|
|
287
291
|
def process_yardoc_tag(comment, tag)
|
288
292
|
in_tag_block = nil
|
289
|
-
|
293
|
+
comment.lines.map do |v|
|
290
294
|
if in_tag_block && v !~ /^\S/
|
291
295
|
Pry::Helpers::Text.strip_color Pry::Helpers::Text.strip_color(v)
|
292
296
|
elsif in_tag_block
|
@@ -328,6 +332,37 @@ class Pry
|
|
328
332
|
code.sub(/\A\s*\/\*.*?\*\/\s*/m, '')
|
329
333
|
end
|
330
334
|
|
335
|
+
def invoke_editor(file, line)
|
336
|
+
if Pry.editor.respond_to?(:call)
|
337
|
+
editor_invocation = Pry.editor.call(file, line)
|
338
|
+
else
|
339
|
+
editor_invocation = "#{Pry.editor} #{start_line_syntax_for_editor(file, line)}"
|
340
|
+
end
|
341
|
+
|
342
|
+
run ".#{editor_invocation}"
|
343
|
+
end
|
344
|
+
|
345
|
+
def start_line_syntax_for_editor(file_name, line_number)
|
346
|
+
file_name = file_name.gsub(/\//, '\\') if RUBY_PLATFORM =~ /mswin|mingw/
|
347
|
+
|
348
|
+
case Pry.editor
|
349
|
+
when /^[gm]?vi/, /^emacs/, /^nano/, /^pico/, /^gedit/, /^kate/
|
350
|
+
"+#{line_number} #{file_name}"
|
351
|
+
when /^mate/, /^geany/
|
352
|
+
"-l #{line_number} #{file_name}"
|
353
|
+
when /^uedit32/
|
354
|
+
"#{file_name}/#{line_number}"
|
355
|
+
when /^jedit/
|
356
|
+
"#{file_name} +line:#{line_number}"
|
357
|
+
else
|
358
|
+
if RUBY_PLATFORM =~ /mswin|mingw/
|
359
|
+
"#{file_name}"
|
360
|
+
else
|
361
|
+
"+#{line_number} #{file_name}"
|
362
|
+
end
|
363
|
+
end
|
364
|
+
end
|
365
|
+
|
331
366
|
def prompt(message, options="Yn")
|
332
367
|
opts = options.scan(/./)
|
333
368
|
optstring = opts.join("/") # case maintained
|
data/lib/pry/helpers/text.rb
CHANGED
@@ -1,10 +1,10 @@
|
|
1
1
|
class Pry
|
2
2
|
module Helpers
|
3
3
|
|
4
|
-
# The methods defined on {Text} are available to custom commands via {Pry::CommandContext#text}.
|
4
|
+
# The methods defined on {Text} are available to custom commands via {Pry::CommandContext#text}.
|
5
5
|
module Text
|
6
|
-
|
7
|
-
COLORS =
|
6
|
+
|
7
|
+
COLORS =
|
8
8
|
{
|
9
9
|
"black" => 0,
|
10
10
|
"red" => 1,
|
@@ -18,7 +18,7 @@ class Pry
|
|
18
18
|
}
|
19
19
|
|
20
20
|
class << self
|
21
|
-
|
21
|
+
|
22
22
|
COLORS.each_pair do |color, value|
|
23
23
|
define_method color do |text|
|
24
24
|
Pry.color ? "\033[0;#{30+value}m#{text}\033[0m" : text.to_s
|
@@ -31,7 +31,7 @@ class Pry
|
|
31
31
|
|
32
32
|
alias_method :grey, :bright_black
|
33
33
|
alias_method :gray, :bright_black
|
34
|
-
|
34
|
+
|
35
35
|
|
36
36
|
# Remove any color codes from _text_.
|
37
37
|
#
|
@@ -41,11 +41,11 @@ class Pry
|
|
41
41
|
text.to_s.gsub(/\e\[.*?(\d)+m/ , '')
|
42
42
|
end
|
43
43
|
|
44
|
-
# Returns _text_ as bold text for use on a terminal.
|
44
|
+
# Returns _text_ as bold text for use on a terminal.
|
45
45
|
# _Pry.color_ must be true for this method to perform any transformations.
|
46
46
|
#
|
47
47
|
# @param [String, #to_s] text
|
48
|
-
# @return [String] _text_
|
48
|
+
# @return [String] _text_
|
49
49
|
def bold text
|
50
50
|
Pry.color ? "\e[1m#{text}\e[0m" : text.to_s
|
51
51
|
end
|
@@ -63,15 +63,15 @@ class Pry
|
|
63
63
|
end
|
64
64
|
|
65
65
|
# Returns _text_ in a numbered list, beginning at _offset_.
|
66
|
-
#
|
66
|
+
#
|
67
67
|
# @param [#each_line] text
|
68
68
|
# @param [Fixnum] offset
|
69
69
|
# @return [String]
|
70
|
-
def with_line_numbers
|
70
|
+
def with_line_numbers(text, offset, color=:blue)
|
71
71
|
lines = text.each_line.to_a
|
72
72
|
lines.each_with_index.map do |line, index|
|
73
73
|
adjusted_index = index + offset
|
74
|
-
"#{self.
|
74
|
+
"#{self.send(color, adjusted_index)}: #{line}"
|
75
75
|
end.join
|
76
76
|
end
|
77
77
|
end
|
data/lib/pry/pry_class.rb
CHANGED
@@ -139,8 +139,33 @@ class Pry
|
|
139
139
|
|
140
140
|
# Load Readline history if required.
|
141
141
|
def self.load_history
|
142
|
-
history_file = File.expand_path(Pry.config.history.file)
|
143
142
|
Readline::HISTORY.push(*File.readlines(history_file).map(&:chomp)) if File.exists?(history_file)
|
143
|
+
@loaded_history = Readline::HISTORY.to_a
|
144
|
+
end
|
145
|
+
|
146
|
+
# Save new lines of Readline history if required.
|
147
|
+
def self.save_history
|
148
|
+
history_to_save = Readline::HISTORY.to_a
|
149
|
+
|
150
|
+
# Omit any history we read from the file.This check is needed because
|
151
|
+
# `hist --clear` would otherwise cause us to not save history in this
|
152
|
+
# session.
|
153
|
+
if history_to_save[0...@loaded_history.size] == @loaded_history
|
154
|
+
history_to_save = history_to_save[@loaded_history.size..-1]
|
155
|
+
end
|
156
|
+
|
157
|
+
File.open(history_file, 'a') do |f|
|
158
|
+
f.puts history_to_save.join("\n") if history_to_save.size > 0
|
159
|
+
end
|
160
|
+
|
161
|
+
# Update @loaded_history so that future calls to save_history
|
162
|
+
# will do the right thing.
|
163
|
+
@loaded_history = Readline::HISTORY.to_a
|
164
|
+
end
|
165
|
+
|
166
|
+
# Get the full path of the history_path for pry.
|
167
|
+
def self.history_file
|
168
|
+
File.expand_path(Pry.config.history.file)
|
144
169
|
end
|
145
170
|
|
146
171
|
# @return [Boolean] Whether this is the first time a Pry session has
|
@@ -180,9 +205,9 @@ class Pry
|
|
180
205
|
|
181
206
|
def self.default_editor_for_platform
|
182
207
|
if RUBY_PLATFORM =~ /mswin|mingw/
|
183
|
-
ENV['EDITOR']
|
208
|
+
ENV['EDITOR'] || "notepad"
|
184
209
|
else
|
185
|
-
ENV['EDITOR']
|
210
|
+
ENV['EDITOR'] || "nano"
|
186
211
|
end
|
187
212
|
end
|
188
213
|
|
@@ -214,7 +239,6 @@ class Pry
|
|
214
239
|
config.history.file = File.expand_path("~/.pry_history")
|
215
240
|
|
216
241
|
config.memory_size = 100
|
217
|
-
config.results_pager = true
|
218
242
|
end
|
219
243
|
|
220
244
|
# Set all the configurable options back to their default values
|
data/lib/pry/pry_instance.rb
CHANGED
@@ -149,7 +149,7 @@ class Pry
|
|
149
149
|
throw :breakout, break_data
|
150
150
|
end
|
151
151
|
|
152
|
-
save_history if Pry.config.history.should_save && finished_top_level_session?
|
152
|
+
Pry.save_history if Pry.config.history.should_save && finished_top_level_session?
|
153
153
|
|
154
154
|
return_value
|
155
155
|
end
|
@@ -217,23 +217,18 @@ class Pry
|
|
217
217
|
target.eval("inp = ::Pry.active_instance.instance_eval { @input_array }")
|
218
218
|
target.eval("out = ::Pry.active_instance.instance_eval { @output_array }")
|
219
219
|
|
220
|
-
@last_result_is_exception = false
|
221
220
|
set_active_instance(target)
|
222
221
|
|
223
222
|
code = r(target)
|
224
223
|
|
225
|
-
Pry.line_buffer.push(*code.each_line)
|
226
224
|
res = set_last_result(target.eval(code, Pry.eval_path, Pry.current_line), target)
|
227
225
|
res
|
228
226
|
rescue SystemExit => e
|
229
227
|
exit
|
230
228
|
rescue Exception => e
|
231
|
-
@last_result_is_exception = true
|
232
|
-
@output_array << e
|
233
229
|
set_last_exception(e, target)
|
234
230
|
ensure
|
235
|
-
|
236
|
-
Pry.current_line += code.each_line.count if code
|
231
|
+
update_input_history(code)
|
237
232
|
end
|
238
233
|
|
239
234
|
# Perform a read.
|
@@ -319,8 +314,10 @@ class Pry
|
|
319
314
|
# @param [Object] result The result.
|
320
315
|
# @param [Binding] target The binding to set `_` on.
|
321
316
|
def set_last_result(result, target)
|
322
|
-
|
317
|
+
@last_result_is_exception = false
|
323
318
|
@output_array << result
|
319
|
+
|
320
|
+
Pry.last_result = result
|
324
321
|
target.eval("_ = ::Pry.last_result")
|
325
322
|
end
|
326
323
|
|
@@ -336,10 +333,39 @@ class Pry
|
|
336
333
|
ex.backtrace.first =~ /(.*):(\d+)/
|
337
334
|
ex.file, ex.line = $1, $2.to_i
|
338
335
|
|
336
|
+
@last_result_is_exception = true
|
337
|
+
@output_array << ex
|
338
|
+
|
339
339
|
Pry.last_exception = ex
|
340
340
|
target.eval("_ex_ = ::Pry.last_exception")
|
341
341
|
end
|
342
342
|
|
343
|
+
# Update Pry's internal state after evalling code.
|
344
|
+
# This method should not need to be invoked directly.
|
345
|
+
# @param [String] code The code we just eval'd
|
346
|
+
def update_input_history(code)
|
347
|
+
# Always push to the @input_array as the @output_array is always pushed to.
|
348
|
+
@input_array << code
|
349
|
+
if code
|
350
|
+
Pry.line_buffer.push(*code.each_line)
|
351
|
+
Pry.current_line += code.each_line.count
|
352
|
+
end
|
353
|
+
if Readline::HISTORY.size > 0
|
354
|
+
|
355
|
+
# all this fluff is to get around annoying bug in libedit on
|
356
|
+
# ruby 1.8.7
|
357
|
+
final_index = -1
|
358
|
+
begin
|
359
|
+
Readline::HISTORY[-1]
|
360
|
+
rescue IndexError
|
361
|
+
final_index = -2
|
362
|
+
end
|
363
|
+
last = Readline::HISTORY[final_index].strip
|
364
|
+
prev = Readline::HISTORY.size > 1 ? Readline::HISTORY[final_index - 1].strip : ''
|
365
|
+
Readline::HISTORY.pop if last && (last.empty? || last == prev)
|
366
|
+
end
|
367
|
+
end
|
368
|
+
|
343
369
|
# Set the active instance for a session.
|
344
370
|
# This method should not need to be invoked directly.
|
345
371
|
# @param [Binding] target The binding to set `_ex_` on.
|
@@ -389,14 +415,6 @@ class Pry
|
|
389
415
|
!@suppress_output || last_result_is_exception?
|
390
416
|
end
|
391
417
|
|
392
|
-
# Save readline history to a file.
|
393
|
-
def save_history
|
394
|
-
history_file = File.expand_path(Pry.config.history.file)
|
395
|
-
File.open(history_file, 'w') do |f|
|
396
|
-
f.write Readline::HISTORY.to_a.join("\n")
|
397
|
-
end
|
398
|
-
end
|
399
|
-
|
400
418
|
# Returns the appropriate prompt to use.
|
401
419
|
# This method should not need to be invoked directly.
|
402
420
|
# @param [Boolean] first_line Whether this is the first line of input
|
data/lib/pry/version.rb
CHANGED
@@ -18,18 +18,6 @@ describe "Pry::CommandProcessor" do
|
|
18
18
|
|
19
19
|
valid = @command_processor.valid_command? "blah"
|
20
20
|
valid.should == false
|
21
|
-
|
22
|
-
|
23
|
-
a = "test-command"
|
24
|
-
|
25
|
-
# not passing in a binding so 'a' shouldn't exist and no command
|
26
|
-
# will be matched
|
27
|
-
valid = @command_processor.valid_command?('#{a}')
|
28
|
-
valid.should == false
|
29
|
-
|
30
|
-
# passing in the optional binding (against which interpolation is performed)
|
31
|
-
valid = @command_processor.valid_command? '#{a}', binding
|
32
|
-
valid.should == true
|
33
21
|
end
|
34
22
|
|
35
23
|
it 'should correctly match a simple string command' do
|
@@ -168,88 +156,21 @@ describe "Pry::CommandProcessor" do
|
|
168
156
|
pos.should == sample_text.size
|
169
157
|
end
|
170
158
|
|
171
|
-
it 'should
|
172
|
-
@pry.commands.command("blah") {}
|
173
|
-
a = "bl"
|
174
|
-
b = "ah"
|
175
|
-
command, captures, pos = @command_processor.command_matched '#{a}#{b}', binding
|
176
|
-
|
177
|
-
command.name.should == "blah"
|
178
|
-
captures.should == []
|
179
|
-
pos.should == command.name.length
|
180
|
-
end
|
181
|
-
|
182
|
-
it 'should correctly match a regex command and interpolation should not break the regex' do
|
183
|
-
regex_command_name = /blah(\d)/
|
184
|
-
@pry.commands.command(regex_command_name) {}
|
185
|
-
|
186
|
-
sample_text = "blah5"
|
187
|
-
a = "5"
|
188
|
-
command, captures, pos = @command_processor.command_matched 'blah#{a}', binding
|
189
|
-
|
190
|
-
command.name.should == regex_command_name
|
191
|
-
captures.should == ["5"]
|
192
|
-
pos.should == sample_text.size
|
193
|
-
end
|
194
|
-
|
195
|
-
it 'should NOT match a regex command that is interpolated when :interpolate => false' do
|
196
|
-
regex_command_name = /blah(\d)/
|
197
|
-
@pry.commands.command(regex_command_name, "", :interpolate => false) {}
|
198
|
-
|
199
|
-
sample_text = "blah5"
|
200
|
-
a = "5"
|
201
|
-
command, captures, pos = @command_processor.command_matched 'blah#{a}', binding
|
202
|
-
|
203
|
-
command.should == nil
|
204
|
-
end
|
205
|
-
|
206
|
-
it 'should correctly match a regex command and interpolation should not break the regex where entire regex command is interpolated' do
|
207
|
-
regex_command_name = /blah(\d)/
|
208
|
-
@pry.commands.command(regex_command_name) {}
|
209
|
-
|
210
|
-
sample_text = "blah5"
|
211
|
-
a = "bl"
|
212
|
-
b = "ah"
|
213
|
-
c = "5"
|
214
|
-
|
215
|
-
command, captures, pos = @command_processor.command_matched '#{a}#{b}#{c}', binding
|
216
|
-
|
217
|
-
command.name.should == regex_command_name
|
218
|
-
captures.should == ["5"]
|
219
|
-
pos.should == sample_text.size
|
220
|
-
end
|
221
|
-
|
222
|
-
it 'should NOT match a regex command where entire regex command is interpolated and :interpolate => false' do
|
223
|
-
regex_command_name = /blah(\d)/
|
224
|
-
@pry.commands.command(regex_command_name, "", :interpolate => false) {}
|
225
|
-
|
226
|
-
sample_text = "blah5"
|
227
|
-
a = "bl"
|
228
|
-
b = "ah"
|
229
|
-
c = "5"
|
230
|
-
|
231
|
-
command, captures, pos = @command_processor.command_matched '#{a}#{b}#{c}', binding
|
232
|
-
command.should == nil
|
233
|
-
end
|
234
|
-
|
235
|
-
it 'should NOT match a command whose name is interpolated when :interpolate => false' do
|
159
|
+
it 'should not interpolate commands that have :interpolate => false (interpolate_string should *not* be called)' do
|
236
160
|
@pry.commands.command("boast", "", :interpolate => false) {}
|
237
|
-
a = "boa"
|
238
|
-
b = "st"
|
239
161
|
|
240
162
|
# remember to use '' instead of "" when testing interpolation or
|
241
163
|
# you'll cause yourself incredible confusion
|
242
|
-
|
243
|
-
|
244
|
-
command.should == nil
|
164
|
+
lambda { @command_processor.command_matched('boast #{c}', binding) }.should.not.raise NameError
|
245
165
|
end
|
246
166
|
|
167
|
+
it 'should only execute the contents of an interpolation once' do
|
168
|
+
$obj = 'a'
|
247
169
|
|
248
|
-
|
249
|
-
|
170
|
+
redirect_pry_io(InputTester.new('cat #{$obj.succ!}'), StringIO.new) do
|
171
|
+
Pry.new.rep
|
172
|
+
end
|
250
173
|
|
251
|
-
|
252
|
-
# you'll cause yourself incredible confusion
|
253
|
-
lambda { @command_processor.command_matched('boast #{c}', binding) }.should.not.raise NameError
|
174
|
+
$obj.should == 'b'
|
254
175
|
end
|
255
176
|
end
|
data/test/test_command_set.rb
CHANGED
@@ -187,4 +187,37 @@ describe Pry::CommandSet do
|
|
187
187
|
@set.command 'foo', "", :listing => 'bar' do;end
|
188
188
|
@set.commands['foo'].options[:listing].should == 'bar'
|
189
189
|
end
|
190
|
+
|
191
|
+
it "should provide a 'help' command" do
|
192
|
+
context = Pry::CommandContext.new
|
193
|
+
context.command_set = @set
|
194
|
+
context.output = StringIO.new
|
195
|
+
|
196
|
+
lambda {
|
197
|
+
@set.run_command(context, 'help')
|
198
|
+
}.should.not.raise
|
199
|
+
end
|
200
|
+
|
201
|
+
it "should sort the output of the 'help' command" do
|
202
|
+
@set.command 'foo', "Fooerizes" do; end
|
203
|
+
@set.command 'goo', "Gooerizes" do; end
|
204
|
+
@set.command 'moo', "Mooerizes" do; end
|
205
|
+
@set.command 'boo', "Booerizes" do; end
|
206
|
+
|
207
|
+
context = Pry::CommandContext.new
|
208
|
+
context.command_set = @set
|
209
|
+
context.output = StringIO.new
|
210
|
+
|
211
|
+
@set.run_command(context, 'help')
|
212
|
+
|
213
|
+
doc = context.output.string
|
214
|
+
|
215
|
+
order = [doc.index("boo"),
|
216
|
+
doc.index("foo"),
|
217
|
+
doc.index("goo"),
|
218
|
+
doc.index("help"),
|
219
|
+
doc.index("moo")]
|
220
|
+
|
221
|
+
order.should == order.sort
|
222
|
+
end
|
190
223
|
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
require 'helper'
|
2
|
+
|
3
|
+
describe Pry::InputCompleter do
|
4
|
+
|
5
|
+
before do
|
6
|
+
# The AMQP gem has some classes like this:
|
7
|
+
# pry(main)> AMQP::Protocol::Test::ContentOk.name
|
8
|
+
# => :content_ok
|
9
|
+
module SymbolyName
|
10
|
+
def self.name; :symboly_name; end
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
after do
|
15
|
+
Object.remove_const :SymbolyName
|
16
|
+
end
|
17
|
+
|
18
|
+
it "should not crash if there's a Module that has a symbolic name." do
|
19
|
+
completer = Pry::InputCompleter.build_completion_proc(Pry.binding_for(Object.new))
|
20
|
+
lambda{ completer.call "a.to_s." }.should.not.raise Exception
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
@@ -321,6 +321,27 @@ describe "Pry::DefaultCommands::Input" do
|
|
321
321
|
str_output.string.each_line.count.should == 4
|
322
322
|
str_output.string.should =~ /b\n\d+:.*c\n\d+:.*d/
|
323
323
|
end
|
324
|
+
|
325
|
+
it "should not contain duplicated lines" do
|
326
|
+
str_output = StringIO.new
|
327
|
+
redirect_pry_io(InputTester.new("3", "_ += 1", "_ += 1", "hist", "exit-all", :history => @hist), str_output) do
|
328
|
+
pry
|
329
|
+
end
|
330
|
+
|
331
|
+
str_output.string.each_line.grep(/_ \+= 1/).count.should == 1
|
332
|
+
end
|
333
|
+
|
334
|
+
it "should not contain duplicated lines" do
|
335
|
+
str_output = StringIO.new
|
336
|
+
redirect_pry_io(InputTester.new(":place_holder", "2 + 2", "", "", "3 + 3", "hist", "exit-all", :history => @hist), str_output) do
|
337
|
+
pry
|
338
|
+
end
|
339
|
+
|
340
|
+
a = str_output.string.each_line.to_a.index{|line| line.include?("2 + 2") }
|
341
|
+
b = str_output.string.each_line.to_a.index{|line| line.include?("3 + 3") }
|
342
|
+
|
343
|
+
(a + 1).should == b
|
344
|
+
end
|
324
345
|
end
|
325
346
|
|
326
347
|
|
@@ -94,7 +94,7 @@ describe "Pry::DefaultCommands::Introspection" do
|
|
94
94
|
|
95
95
|
it 'should output an instance method\'s source for a method defined inside pry using define_method' do
|
96
96
|
str_output = StringIO.new
|
97
|
-
redirect_pry_io(InputTester.new("class A", "define_method(:yup) {}", "end", "
|
97
|
+
redirect_pry_io(InputTester.new("class A", "define_method(:yup) {}", "end", "show-method A#yup"), str_output) do
|
98
98
|
TOPLEVEL_BINDING.pry
|
99
99
|
end
|
100
100
|
|
data/test/test_pry.rb
CHANGED
@@ -517,7 +517,7 @@ describe Pry do
|
|
517
517
|
$test_interpolation = nil
|
518
518
|
end
|
519
519
|
|
520
|
-
# bug fix for https://github.com/
|
520
|
+
# bug fix for https://github.com/pry/pry/issues/170
|
521
521
|
it 'should not choke on complex string interpolation when checking if ruby code is a command' do
|
522
522
|
redirect_pry_io(InputTester.new('/#{Regexp.escape(File.expand_path("."))}/'), str_output = StringIO.new) do
|
523
523
|
pry
|
@@ -0,0 +1,82 @@
|
|
1
|
+
require 'helper'
|
2
|
+
require 'tempfile'
|
3
|
+
|
4
|
+
describe Pry do
|
5
|
+
|
6
|
+
before do
|
7
|
+
Readline::HISTORY.shift while Readline::HISTORY.length > 0
|
8
|
+
@hist = Tempfile.new(["tmp", ".pry_history"]).tap(&:close).path
|
9
|
+
File.open(@hist, 'w') {|f| f << "1\n2\n3\n" }
|
10
|
+
@old_hist = Pry.config.history.file
|
11
|
+
Pry.config.history.file = @hist
|
12
|
+
Pry.load_history
|
13
|
+
end
|
14
|
+
|
15
|
+
after do
|
16
|
+
File.unlink @hist
|
17
|
+
Pry.config.history.file = @old_hist
|
18
|
+
end
|
19
|
+
|
20
|
+
describe ".load_history" do
|
21
|
+
it "should read the contents of the file" do
|
22
|
+
Readline::HISTORY.to_a[-2..-1].should === ["2", "3"]
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
describe ".save_history" do
|
27
|
+
it "should include a trailing newline" do
|
28
|
+
Readline::HISTORY << "4"
|
29
|
+
Pry.save_history
|
30
|
+
File.read(@hist).should =~ /4\n\z/
|
31
|
+
end
|
32
|
+
|
33
|
+
it "should not change anything if history is not changed" do
|
34
|
+
File.open(@hist, 'w') {|f| f << "4\n5\n6\n" }
|
35
|
+
Pry.save_history
|
36
|
+
File.read(@hist).should == "4\n5\n6\n"
|
37
|
+
end
|
38
|
+
|
39
|
+
it "should append new lines to the file" do
|
40
|
+
Readline::HISTORY << "4"
|
41
|
+
Pry.save_history
|
42
|
+
File.read(@hist).should == "1\n2\n3\n4\n"
|
43
|
+
end
|
44
|
+
|
45
|
+
it "should not clobber lines written by other Pry's in the meantime" do
|
46
|
+
Readline::HISTORY << "5"
|
47
|
+
File.open(@hist, 'a') {|f| f << "4\n" }
|
48
|
+
Pry.save_history
|
49
|
+
|
50
|
+
Readline::HISTORY.to_a[-3..-1].should == ["2", "3", "5"]
|
51
|
+
File.read(@hist).should == "1\n2\n3\n4\n5\n"
|
52
|
+
end
|
53
|
+
|
54
|
+
it "should not delete lines from the file if this session's history was cleared" do
|
55
|
+
Readline::HISTORY.pop while Readline::HISTORY.size > 0
|
56
|
+
Pry.save_history
|
57
|
+
File.read(@hist).should == "1\n2\n3\n"
|
58
|
+
end
|
59
|
+
|
60
|
+
it "should save new lines that are added after the history was cleared" do
|
61
|
+
Readline::HISTORY.pop while Readline::HISTORY.size > 0
|
62
|
+
Readline::HISTORY << "4"
|
63
|
+
|
64
|
+
# doing this twice as libedit on 1.8.7 has bugs and sometimes ignores the
|
65
|
+
# first line in history
|
66
|
+
Readline::HISTORY << "4"
|
67
|
+
Pry.save_history
|
68
|
+
File.read(@hist).should =~ /1\n2\n3\n4\n/
|
69
|
+
end
|
70
|
+
|
71
|
+
it "should only append new lines the second time it is saved" do
|
72
|
+
Readline::HISTORY << "4"
|
73
|
+
Pry.save_history
|
74
|
+
File.open(@hist, 'a') {|f| f << "5\n" }
|
75
|
+
Readline::HISTORY << "6"
|
76
|
+
Pry.save_history
|
77
|
+
|
78
|
+
Readline::HISTORY.to_a[-4..-1].should == ["2", "3", "4", "6"]
|
79
|
+
File.read(@hist).should == "1\n2\n3\n4\n5\n6\n"
|
80
|
+
end
|
81
|
+
end
|
82
|
+
end
|
metadata
CHANGED
@@ -1,8 +1,8 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: pry
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
prerelease:
|
5
|
-
version: 0.9.
|
4
|
+
prerelease: 5
|
5
|
+
version: 0.9.4pre1
|
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-
|
13
|
+
date: 2011-08-19 00:00:00 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: ruby_parser
|
@@ -92,6 +92,7 @@ files:
|
|
92
92
|
- .gitignore
|
93
93
|
- .yardopts
|
94
94
|
- CHANGELOG
|
95
|
+
- CONTRIBUTORS
|
95
96
|
- LICENSE
|
96
97
|
- README.markdown
|
97
98
|
- Rakefile
|
@@ -142,6 +143,7 @@ files:
|
|
142
143
|
- test/test_command_helpers.rb
|
143
144
|
- test/test_command_processor.rb
|
144
145
|
- test/test_command_set.rb
|
146
|
+
- test/test_completion.rb
|
145
147
|
- test/test_default_commands.rb
|
146
148
|
- test/test_default_commands/test_context.rb
|
147
149
|
- test/test_default_commands/test_documentation.rb
|
@@ -150,6 +152,7 @@ files:
|
|
150
152
|
- test/test_default_commands/test_introspection.rb
|
151
153
|
- test/test_history_array.rb
|
152
154
|
- test/test_pry.rb
|
155
|
+
- test/test_pry_history.rb
|
153
156
|
- test/testrc
|
154
157
|
- wiki/Customizing-pry.md
|
155
158
|
- wiki/Home.md
|
@@ -170,9 +173,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
170
173
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
171
174
|
none: false
|
172
175
|
requirements:
|
173
|
-
- - "
|
176
|
+
- - ">"
|
174
177
|
- !ruby/object:Gem::Version
|
175
|
-
version:
|
178
|
+
version: 1.3.1
|
176
179
|
requirements: []
|
177
180
|
|
178
181
|
rubyforge_project:
|
@@ -185,6 +188,7 @@ test_files:
|
|
185
188
|
- test/test_command_helpers.rb
|
186
189
|
- test/test_command_processor.rb
|
187
190
|
- test/test_command_set.rb
|
191
|
+
- test/test_completion.rb
|
188
192
|
- test/test_default_commands.rb
|
189
193
|
- test/test_default_commands/test_context.rb
|
190
194
|
- test/test_default_commands/test_documentation.rb
|
@@ -193,4 +197,5 @@ test_files:
|
|
193
197
|
- test/test_default_commands/test_introspection.rb
|
194
198
|
- test/test_history_array.rb
|
195
199
|
- test/test_pry.rb
|
200
|
+
- test/test_pry_history.rb
|
196
201
|
- test/testrc
|