pry 0.9.10pre1-i386-mswin32 → 0.9.11-i386-mswin32

Sign up to get free protection for your applications and to get access to all the features.
Files changed (194) hide show
  1. data/.travis.yml +3 -1
  2. data/CHANGELOG +63 -2
  3. data/CONTRIBUTORS +43 -25
  4. data/Gemfile +7 -0
  5. data/Guardfile +62 -0
  6. data/README.markdown +4 -4
  7. data/Rakefile +34 -35
  8. data/lib/pry.rb +107 -54
  9. data/lib/pry/cli.rb +34 -11
  10. data/lib/pry/code.rb +165 -182
  11. data/lib/pry/code/code_range.rb +70 -0
  12. data/lib/pry/code/loc.rb +92 -0
  13. data/lib/pry/code_object.rb +153 -0
  14. data/lib/pry/command.rb +160 -22
  15. data/lib/pry/command_set.rb +37 -26
  16. data/lib/pry/commands.rb +4 -27
  17. data/lib/pry/commands/amend_line.rb +99 -0
  18. data/lib/pry/commands/bang.rb +20 -0
  19. data/lib/pry/commands/bang_pry.rb +17 -0
  20. data/lib/pry/commands/cat.rb +53 -0
  21. data/lib/pry/commands/cat/abstract_formatter.rb +27 -0
  22. data/lib/pry/commands/cat/exception_formatter.rb +78 -0
  23. data/lib/pry/commands/cat/file_formatter.rb +84 -0
  24. data/lib/pry/commands/cat/input_expression_formatter.rb +43 -0
  25. data/lib/pry/commands/cd.rb +30 -0
  26. data/lib/pry/commands/code_collector.rb +165 -0
  27. data/lib/pry/commands/deprecated_commands.rb +2 -0
  28. data/lib/pry/commands/disable_pry.rb +27 -0
  29. data/lib/pry/commands/easter_eggs.rb +112 -0
  30. data/lib/pry/commands/edit.rb +206 -0
  31. data/lib/pry/commands/edit/exception_patcher.rb +25 -0
  32. data/lib/pry/commands/edit/file_and_line_locator.rb +38 -0
  33. data/lib/pry/commands/edit/method_patcher.rb +122 -0
  34. data/lib/pry/commands/exit.rb +42 -0
  35. data/lib/pry/commands/exit_all.rb +29 -0
  36. data/lib/pry/commands/exit_program.rb +24 -0
  37. data/lib/pry/commands/find_method.rb +199 -0
  38. data/lib/pry/commands/fix_indent.rb +19 -0
  39. data/lib/pry/commands/gem_cd.rb +26 -0
  40. data/lib/pry/commands/gem_install.rb +29 -0
  41. data/lib/pry/commands/gem_list.rb +33 -0
  42. data/lib/pry/commands/gem_open.rb +29 -0
  43. data/lib/pry/commands/gist.rb +95 -0
  44. data/lib/pry/commands/help.rb +164 -0
  45. data/lib/pry/commands/hist.rb +161 -0
  46. data/lib/pry/commands/import_set.rb +22 -0
  47. data/lib/pry/commands/install_command.rb +51 -0
  48. data/lib/pry/commands/jump_to.rb +29 -0
  49. data/lib/pry/commands/ls.rb +339 -0
  50. data/lib/pry/commands/nesting.rb +25 -0
  51. data/lib/pry/commands/play.rb +69 -0
  52. data/lib/pry/commands/pry_backtrace.rb +26 -0
  53. data/lib/pry/commands/pry_version.rb +17 -0
  54. data/lib/pry/commands/raise_up.rb +32 -0
  55. data/lib/pry/commands/reload_code.rb +39 -0
  56. data/lib/pry/commands/reset.rb +18 -0
  57. data/lib/pry/commands/ri.rb +56 -0
  58. data/lib/pry/commands/save_file.rb +61 -0
  59. data/lib/pry/commands/shell_command.rb +43 -0
  60. data/lib/pry/commands/shell_mode.rb +27 -0
  61. data/lib/pry/commands/show_doc.rb +78 -0
  62. data/lib/pry/commands/show_info.rb +139 -0
  63. data/lib/pry/commands/show_input.rb +17 -0
  64. data/lib/pry/commands/show_source.rb +37 -0
  65. data/lib/pry/commands/simple_prompt.rb +22 -0
  66. data/lib/pry/commands/stat.rb +40 -0
  67. data/lib/pry/commands/switch_to.rb +23 -0
  68. data/lib/pry/commands/toggle_color.rb +20 -0
  69. data/lib/pry/commands/whereami.rb +114 -0
  70. data/lib/pry/commands/wtf.rb +57 -0
  71. data/lib/pry/completion.rb +120 -46
  72. data/lib/pry/config.rb +11 -0
  73. data/lib/pry/core_extensions.rb +30 -19
  74. data/lib/pry/editor.rb +129 -0
  75. data/lib/pry/helpers.rb +1 -0
  76. data/lib/pry/helpers/base_helpers.rb +89 -119
  77. data/lib/pry/helpers/command_helpers.rb +7 -122
  78. data/lib/pry/helpers/table.rb +100 -0
  79. data/lib/pry/helpers/text.rb +4 -4
  80. data/lib/pry/history_array.rb +5 -0
  81. data/lib/pry/hooks.rb +1 -3
  82. data/lib/pry/indent.rb +104 -30
  83. data/lib/pry/method.rb +66 -22
  84. data/lib/pry/module_candidate.rb +26 -15
  85. data/lib/pry/pager.rb +70 -0
  86. data/lib/pry/plugins.rb +1 -2
  87. data/lib/pry/pry_class.rb +63 -22
  88. data/lib/pry/pry_instance.rb +58 -37
  89. data/lib/pry/rubygem.rb +74 -0
  90. data/lib/pry/terminal_info.rb +43 -0
  91. data/lib/pry/test/helper.rb +185 -0
  92. data/lib/pry/version.rb +1 -1
  93. data/lib/pry/wrapped_module.rb +58 -24
  94. data/pry.gemspec +21 -37
  95. data/{test/test_cli.rb → spec/cli_spec.rb} +0 -0
  96. data/spec/code_object_spec.rb +277 -0
  97. data/{test/test_code.rb → spec/code_spec.rb} +19 -1
  98. data/{test/test_command_helpers.rb → spec/command_helpers_spec.rb} +0 -0
  99. data/{test/test_command_integration.rb → spec/command_integration_spec.rb} +38 -46
  100. data/{test/test_command_set.rb → spec/command_set_spec.rb} +18 -1
  101. data/{test/test_command.rb → spec/command_spec.rb} +250 -149
  102. data/spec/commands/amend_line_spec.rb +247 -0
  103. data/spec/commands/bang_spec.rb +19 -0
  104. data/spec/commands/cat_spec.rb +164 -0
  105. data/spec/commands/cd_spec.rb +250 -0
  106. data/spec/commands/disable_pry_spec.rb +25 -0
  107. data/spec/commands/edit_spec.rb +727 -0
  108. data/spec/commands/exit_all_spec.rb +34 -0
  109. data/spec/commands/exit_program_spec.rb +19 -0
  110. data/spec/commands/exit_spec.rb +34 -0
  111. data/{test/test_default_commands/test_find_method.rb → spec/commands/find_method_spec.rb} +27 -7
  112. data/spec/commands/gem_list_spec.rb +26 -0
  113. data/spec/commands/gist_spec.rb +75 -0
  114. data/{test/test_default_commands/test_help.rb → spec/commands/help_spec.rb} +8 -9
  115. data/spec/commands/hist_spec.rb +181 -0
  116. data/spec/commands/jump_to_spec.rb +15 -0
  117. data/spec/commands/ls_spec.rb +177 -0
  118. data/spec/commands/play_spec.rb +140 -0
  119. data/spec/commands/raise_up_spec.rb +56 -0
  120. data/spec/commands/save_file_spec.rb +177 -0
  121. data/spec/commands/show_doc_spec.rb +378 -0
  122. data/spec/commands/show_input_spec.rb +17 -0
  123. data/spec/commands/show_source_spec.rb +597 -0
  124. data/spec/commands/whereami_spec.rb +154 -0
  125. data/spec/completion_spec.rb +233 -0
  126. data/spec/control_d_handler_spec.rb +58 -0
  127. data/spec/editor_spec.rb +79 -0
  128. data/{test/test_exception_whitelist.rb → spec/exception_whitelist_spec.rb} +0 -0
  129. data/{test → spec/fixtures}/candidate_helper1.rb +0 -0
  130. data/{test → spec/fixtures}/candidate_helper2.rb +0 -0
  131. data/{test/test_default_commands → spec/fixtures}/example.erb +0 -0
  132. data/spec/fixtures/example_nesting.rb +33 -0
  133. data/spec/fixtures/show_source_doc_examples.rb +15 -0
  134. data/{test → spec/fixtures}/testrc +0 -0
  135. data/{test → spec/fixtures}/testrcbad +0 -0
  136. data/spec/helper.rb +34 -0
  137. data/spec/helpers/bacon.rb +86 -0
  138. data/spec/helpers/mock_pry.rb +43 -0
  139. data/spec/helpers/table_spec.rb +83 -0
  140. data/{test/test_history_array.rb → spec/history_array_spec.rb} +21 -19
  141. data/{test/test_hooks.rb → spec/hooks_spec.rb} +0 -0
  142. data/{test/test_indent.rb → spec/indent_spec.rb} +24 -0
  143. data/{test/test_input_stack.rb → spec/input_stack_spec.rb} +4 -0
  144. data/{test/test_method.rb → spec/method_spec.rb} +65 -1
  145. data/{test/test_prompt.rb → spec/prompt_spec.rb} +0 -0
  146. data/{test/test_pry_defaults.rb → spec/pry_defaults_spec.rb} +14 -14
  147. data/{test/test_pry_history.rb → spec/pry_history_spec.rb} +15 -0
  148. data/spec/pry_output_spec.rb +95 -0
  149. data/{test/test_pry.rb → spec/pry_spec.rb} +74 -32
  150. data/{test/test_sticky_locals.rb → spec/sticky_locals_spec.rb} +27 -25
  151. data/{test/test_syntax_checking.rb → spec/syntax_checking_spec.rb} +17 -1
  152. data/{test/test_wrapped_module.rb → spec/wrapped_module_spec.rb} +92 -5
  153. metadata +239 -115
  154. data/examples/example_basic.rb +0 -15
  155. data/examples/example_command_override.rb +0 -32
  156. data/examples/example_commands.rb +0 -36
  157. data/examples/example_hooks.rb +0 -9
  158. data/examples/example_image_edit.rb +0 -67
  159. data/examples/example_input.rb +0 -7
  160. data/examples/example_input2.rb +0 -29
  161. data/examples/example_output.rb +0 -11
  162. data/examples/example_print.rb +0 -6
  163. data/examples/example_prompt.rb +0 -9
  164. data/examples/helper.rb +0 -6
  165. data/lib/pry/default_commands/cd.rb +0 -81
  166. data/lib/pry/default_commands/commands.rb +0 -62
  167. data/lib/pry/default_commands/context.rb +0 -98
  168. data/lib/pry/default_commands/easter_eggs.rb +0 -95
  169. data/lib/pry/default_commands/editing.rb +0 -420
  170. data/lib/pry/default_commands/find_method.rb +0 -169
  171. data/lib/pry/default_commands/gems.rb +0 -84
  172. data/lib/pry/default_commands/gist.rb +0 -187
  173. data/lib/pry/default_commands/help.rb +0 -127
  174. data/lib/pry/default_commands/hist.rb +0 -120
  175. data/lib/pry/default_commands/input_and_output.rb +0 -306
  176. data/lib/pry/default_commands/introspection.rb +0 -410
  177. data/lib/pry/default_commands/ls.rb +0 -272
  178. data/lib/pry/default_commands/misc.rb +0 -38
  179. data/lib/pry/default_commands/navigating_pry.rb +0 -110
  180. data/lib/pry/default_commands/whereami.rb +0 -92
  181. data/lib/pry/extended_commands/experimental.rb +0 -7
  182. data/test/helper.rb +0 -223
  183. data/test/test_completion.rb +0 -62
  184. data/test/test_control_d_handler.rb +0 -45
  185. data/test/test_default_commands/test_cd.rb +0 -321
  186. data/test/test_default_commands/test_context.rb +0 -288
  187. data/test/test_default_commands/test_documentation.rb +0 -315
  188. data/test/test_default_commands/test_gems.rb +0 -18
  189. data/test/test_default_commands/test_input.rb +0 -428
  190. data/test/test_default_commands/test_introspection.rb +0 -511
  191. data/test/test_default_commands/test_ls.rb +0 -151
  192. data/test/test_default_commands/test_shell.rb +0 -343
  193. data/test/test_default_commands/test_show_source.rb +0 -432
  194. data/test/test_pry_output.rb +0 -41
@@ -0,0 +1,25 @@
1
+ require 'helper'
2
+
3
+ describe "disable-pry" do
4
+ before do
5
+ @t = pry_tester
6
+ end
7
+
8
+ after do
9
+ ENV.delete 'DISABLE_PRY'
10
+ end
11
+
12
+ it 'should quit the current session' do
13
+ lambda{
14
+ @t.process_command 'disable-pry'
15
+ }.should.throw(:breakout)
16
+ end
17
+
18
+ it "should set DISABLE_PRY" do
19
+ ENV['DISABLE_PRY'].should == nil
20
+ lambda{
21
+ @t.process_command 'disable-pry'
22
+ }.should.throw(:breakout)
23
+ ENV['DISABLE_PRY'].should == 'true'
24
+ end
25
+ end
@@ -0,0 +1,727 @@
1
+ require 'pathname'
2
+ require 'helper'
3
+
4
+ describe "edit" do
5
+ before do
6
+ @old_editor = Pry.config.editor
7
+ @file = @line = @contents = nil
8
+ Pry.config.editor = lambda do |file, line|
9
+ @file = file; @line = line; @contents = File.read(@file)
10
+ nil
11
+ end
12
+ end
13
+
14
+ after do
15
+ Pry.config.editor = @old_editor
16
+ end
17
+
18
+ describe "with FILE" do
19
+
20
+ before do
21
+ # OS-specific tempdir name. For GNU/Linux it's "tmp", for Windows it's
22
+ # something "Temp".
23
+ @tf_dir =
24
+ if Pry::Helpers::BaseHelpers.mri_19?
25
+ Pathname.new(Dir::Tmpname.tmpdir)
26
+ else
27
+ Pathname.new(Dir.tmpdir)
28
+ end
29
+
30
+ @tf_path = File.expand_path(File.join(@tf_dir.to_s, 'bar.rb'))
31
+ FileUtils.touch(@tf_path)
32
+ end
33
+
34
+ after do
35
+ FileUtils.rm(@tf_path) if File.exists?(@tf_path)
36
+ end
37
+
38
+ it "should invoke Pry.config.editor with absolutified filenames" do
39
+ pry_eval 'edit lib/pry.rb'
40
+ @file.should == File.expand_path('lib/pry.rb')
41
+
42
+ pry_eval "edit #@tf_path"
43
+ @file.should == @tf_path
44
+ end
45
+
46
+ it "should guess the line number from a colon" do
47
+ pry_eval 'edit lib/pry.rb:10'
48
+ @line.should == 10
49
+ end
50
+
51
+ it "should use the line number from -l" do
52
+ pry_eval 'edit -l 10 lib/pry.rb'
53
+ @line.should == 10
54
+ end
55
+
56
+ it "should not delete the file!" do
57
+ pry_eval 'edit Rakefile'
58
+ File.exist?(@file).should == true
59
+ end
60
+
61
+ it "works with files that contain blanks in their names" do
62
+ tf_path = File.join(File.dirname(@tf_path), 'swoop and doop.rb')
63
+ FileUtils.touch(tf_path)
64
+ pry_eval "edit #{ tf_path }"
65
+ @file.should == tf_path
66
+ FileUtils.rm(tf_path)
67
+ end
68
+
69
+ describe do
70
+ before do
71
+ Pad.counter = 0
72
+ Pry.config.editor = lambda { |file, line|
73
+ File.open(file, 'w') { |f| f << "Pad.counter = Pad.counter + 1" }
74
+ nil
75
+ }
76
+ end
77
+
78
+ it "should reload the file if it is a ruby file" do
79
+ temp_file do |tf|
80
+ counter = Pad.counter
81
+ path = tf.path
82
+
83
+ pry_eval "edit #{path}"
84
+
85
+ Pad.counter.should == counter + 1
86
+ end
87
+ end
88
+
89
+ it "should not reload the file if it is not a ruby file" do
90
+ temp_file('.py') do |tf|
91
+ counter = Pad.counter
92
+ path = tf.path
93
+
94
+ pry_eval "edit #{path}"
95
+
96
+ Pad.counter.should == counter
97
+ end
98
+ end
99
+
100
+ it "should not reload a ruby file if -n is given" do
101
+ temp_file do |tf|
102
+ counter = Pad.counter
103
+ path = tf.path
104
+
105
+ Pad.counter.should == counter
106
+ end
107
+ end
108
+
109
+ it "should reload a non-ruby file if -r is given" do
110
+ temp_file('.pryrc') do |tf|
111
+ counter = Pad.counter
112
+ path = tf.path
113
+
114
+ pry_eval "edit -r #{path}"
115
+
116
+ Pad.counter.should == counter + 1
117
+ end
118
+ end
119
+ end
120
+
121
+ describe do
122
+ before do
123
+ @reloading = nil
124
+ Pry.config.editor = lambda do |file, line, reloading|
125
+ @file = file; @line = line; @reloading = reloading
126
+ nil
127
+ end
128
+ end
129
+
130
+ it "should pass the editor a reloading arg" do
131
+ pry_eval 'edit lib/pry.rb'
132
+ @reloading.should == true
133
+ pry_eval 'edit -n lib/pry.rb'
134
+ @reloading.should == false
135
+ end
136
+ end
137
+ end
138
+
139
+ describe "with --ex" do
140
+ before do
141
+ @t = pry_tester do
142
+ def last_exception=(exception)
143
+ @pry.last_exception = exception
144
+ end
145
+ def last_exception; @pry.last_exception; end
146
+ end
147
+ end
148
+
149
+ describe "with a real file" do
150
+ before do
151
+ @tf = Tempfile.new(["pry", ".rb"])
152
+ @path = @tf.path
153
+ @tf << "1\n2\nraise RuntimeError"
154
+ @tf.flush
155
+
156
+ begin
157
+ load @path
158
+ rescue RuntimeError => e
159
+ @t.last_exception = e
160
+ end
161
+ end
162
+
163
+ after do
164
+ @tf.close(true)
165
+ File.unlink("#{@path}c") if File.exists?("#{@path}c") #rbx
166
+ end
167
+
168
+ it "should reload the file" do
169
+ Pry.config.editor = lambda {|file, line|
170
+ File.open(file, 'w'){|f| f << "FOO = 'BAR'" }
171
+ nil
172
+ }
173
+
174
+ defined?(FOO).should.be.nil
175
+
176
+ @t.eval 'edit --ex'
177
+
178
+ FOO.should == 'BAR'
179
+ end
180
+
181
+ # regression test (this used to edit the current method instead
182
+ # of the exception)
183
+ it 'edits the exception even when in a patched method context' do
184
+ source_location = nil
185
+ Pry.config.editor = lambda {|file, line|
186
+ source_location = [file, line]
187
+ nil
188
+ }
189
+
190
+ Pad.le = @t.last_exception
191
+ redirect_pry_io(InputTester.new("def broken_method", "binding.pry", "end",
192
+ "broken_method",
193
+ "_pry_.last_exception = Pad.le",
194
+ "edit --ex -n", "exit-all", "exit-all")) do
195
+ Object.new.pry
196
+ end
197
+
198
+ source_location.should == [@path, 3]
199
+ Pad.clear
200
+ end
201
+
202
+ it "should not reload the file if -n is passed" do
203
+ Pry.config.editor = lambda {|file, line|
204
+ File.open(file, 'w'){|f| f << "FOO2 = 'BAZ'" }
205
+ nil
206
+ }
207
+
208
+ defined?(FOO2).should.be.nil
209
+
210
+ @t.eval 'edit -n --ex'
211
+
212
+ defined?(FOO2).should.be.nil
213
+ end
214
+
215
+ describe "with --patch" do
216
+ # Original source code must be untouched.
217
+ it "should apply changes only in memory (monkey patching)" do
218
+ Pry.config.editor = lambda {|file, line|
219
+ File.open(file, 'w'){|f| f << "FOO3 = 'PIYO'" }
220
+ @patched_def = File.open(file, 'r').read
221
+ nil
222
+ }
223
+
224
+ defined?(FOO3).should.be.nil
225
+
226
+ @t.eval 'edit --ex --patch'
227
+
228
+ FOO3.should == 'PIYO'
229
+
230
+ @tf.rewind
231
+ @tf.read.should == "1\n2\nraise RuntimeError"
232
+ @patched_def.should == "FOO3 = 'PIYO'"
233
+ end
234
+ end
235
+ end
236
+
237
+ describe "with --ex NUM" do
238
+ before do
239
+ Pry.config.editor = proc do |file, line|
240
+ @__ex_file__ = file
241
+ @__ex_line__ = line
242
+ nil
243
+ end
244
+
245
+ @t.last_exception = mock_exception('a:1', 'b:2', 'c:3')
246
+ end
247
+
248
+ it 'should start on first level of backtrace with just --ex' do
249
+ @t.eval 'edit -n --ex'
250
+ @__ex_file__.should == "a"
251
+ @__ex_line__.should == 1
252
+ end
253
+
254
+ it 'should start editor on first level of backtrace with --ex 0' do
255
+ @t.eval 'edit -n --ex 0'
256
+ @__ex_file__.should == "a"
257
+ @__ex_line__.should == 1
258
+ end
259
+
260
+ it 'should start editor on second level of backtrace with --ex 1' do
261
+ @t.eval 'edit -n --ex 1'
262
+ @__ex_file__.should == "b"
263
+ @__ex_line__.should == 2
264
+ end
265
+
266
+ it 'should start editor on third level of backtrace with --ex 2' do
267
+ @t.eval 'edit -n --ex 2'
268
+ @__ex_file__.should == "c"
269
+ @__ex_line__.should == 3
270
+ end
271
+
272
+ it 'should display error message when backtrace level is invalid' do
273
+ proc {
274
+ @t.eval 'edit -n --ex 4'
275
+ }.should.raise(Pry::CommandError)
276
+ end
277
+ end
278
+ end
279
+
280
+ describe "without FILE" do
281
+ before do
282
+ @t = pry_tester
283
+ end
284
+
285
+ it "should edit the current expression if it's incomplete" do
286
+ eval_str = 'def a'
287
+ @t.process_command 'edit', eval_str
288
+ @contents.should == "def a\n"
289
+ end
290
+
291
+ it "should edit the previous expression if the current is empty" do
292
+ @t.eval 'def a; 2; end', 'edit'
293
+ @contents.should == "def a; 2; end\n"
294
+ end
295
+
296
+ it "should use a blank file if -t is specified" do
297
+ @t.eval 'def a; 5; end', 'edit -t'
298
+ @contents.should == "\n"
299
+ end
300
+
301
+ it "should use a blank file if -t given, even during an expression" do
302
+ eval_str = 'def a;'
303
+ @t.process_command 'edit -t', eval_str
304
+ @contents.should == "\n"
305
+ end
306
+
307
+ it "should position the cursor at the end of the expression" do
308
+ eval_str = "def a; 2;\nend"
309
+ @t.process_command 'edit', eval_str
310
+ @line.should == 2
311
+ end
312
+
313
+ it "should evaluate the expression" do
314
+ Pry.config.editor = lambda {|file, line|
315
+ File.open(file, 'w'){|f| f << "'FOO'\n" }
316
+ nil
317
+ }
318
+ eval_str = ''
319
+ @t.process_command 'edit', eval_str
320
+ eval_str.should == "'FOO'\n"
321
+ end
322
+
323
+ it "should not evaluate the expression with -n" do
324
+ Pry.config.editor = lambda {|file, line|
325
+ File.open(file, 'w'){|f| f << "'FOO'\n" }
326
+ nil
327
+ }
328
+ eval_str = ''
329
+ @t.process_command 'edit -n', eval_str
330
+ eval_str.should == ''
331
+ end
332
+ end
333
+
334
+ describe "with --in" do
335
+ it "should edit the nth line of _in_" do
336
+ pry_eval '10', '11', 'edit --in -2'
337
+ @contents.should == "10\n"
338
+ end
339
+
340
+ it "should edit the last line if no argument is given" do
341
+ pry_eval '10', '11', 'edit --in'
342
+ @contents.should == "11\n"
343
+ end
344
+
345
+ it "should edit a range of lines if a range is given" do
346
+ pry_eval "10", "11", "edit -i 1,2"
347
+ @contents.should == "10\n11\n"
348
+ end
349
+
350
+ it "should edit a multi-line expression as it occupies one line of _in_" do
351
+ pry_eval "class Fixnum\n def invert; -self; end\nend", "edit -i 1"
352
+ @contents.should == "class Fixnum\n def invert; -self; end\nend\n"
353
+ end
354
+
355
+ it "should not work with a filename" do
356
+ proc {
357
+ pry_eval 'edit ruby.rb -i'
358
+ }.should.raise(Pry::CommandError).
359
+ message.should =~ /Only one of --ex, --temp, --in, --method and FILE/
360
+ end
361
+
362
+ it "should not work with nonsense" do
363
+ proc {
364
+ pry_eval 'edit --in three'
365
+ }.should.raise(Pry::CommandError).
366
+ message.should =~ /Not a valid range: three/
367
+ end
368
+ end
369
+
370
+ describe "old edit-method tests now migrated to edit" do
371
+ describe "on a method defined in a file" do
372
+ before do
373
+ @tempfile = (Tempfile.new(['pry', '.rb']))
374
+ @tempfile.puts <<-EOS
375
+ module A
376
+ def a
377
+ :yup
378
+ end
379
+
380
+ def b
381
+ :kinda
382
+ end
383
+ end
384
+
385
+ class X
386
+ include A
387
+
388
+ def self.x
389
+ :double_yup
390
+ end
391
+
392
+ def x
393
+ :nope
394
+ end
395
+
396
+ def b
397
+ super
398
+ end
399
+ alias c b
400
+
401
+ def y?
402
+ :because
403
+ end
404
+
405
+ class B
406
+ G = :nawt
407
+
408
+ def foo
409
+ :possibly
410
+ G
411
+ end
412
+ end
413
+ end
414
+ EOS
415
+ @tempfile.flush
416
+ load @tempfile.path
417
+
418
+ @tempfile_path = @tempfile.path
419
+ end
420
+
421
+ after do
422
+ @tempfile.close(true)
423
+ end
424
+
425
+ describe 'without -p' do
426
+ before do
427
+ @file = @line = @contents = nil
428
+ Pry.config.editor = lambda do |file, line|
429
+ @file = file; @line = line
430
+ nil
431
+ end
432
+ end
433
+
434
+ it "should correctly find a class method" do
435
+ pry_eval 'edit X.x'
436
+
437
+ @file.should == @tempfile_path
438
+ @line.should == 14
439
+
440
+ end
441
+
442
+ it "should correctly find an instance method" do
443
+ pry_eval 'edit X#x'
444
+ @file.should == @tempfile_path
445
+ @line.should == 18
446
+ end
447
+
448
+ it "should correctly find a method on an instance" do
449
+ pry_eval 'x = X.new', 'edit x.x'
450
+ @file.should == @tempfile_path
451
+ @line.should == 18
452
+ end
453
+
454
+ it "should correctly find a method from a module" do
455
+ pry_eval 'edit X#a'
456
+ @file.should == @tempfile_path
457
+ @line.should == 2
458
+ end
459
+
460
+ it "should correctly find an aliased method" do
461
+ pry_eval 'edit X#c'
462
+ @file.should == @tempfile_path
463
+ @line.should == 22
464
+ end
465
+ end
466
+
467
+ describe 'with -p' do
468
+ before do
469
+ Pry.config.editor = lambda do |file, line|
470
+ lines = File.read(file).lines.to_a
471
+ lines[1] = ":maybe\n"
472
+ File.open(file, 'w') do |f|
473
+ f.write(lines.join)
474
+ end
475
+ @patched_def = String(lines[1]).chomp
476
+ nil
477
+ end
478
+ end
479
+
480
+ it "should successfully replace a class method" do
481
+ pry_eval 'edit -p X.x'
482
+
483
+ class << X
484
+ X.method(:x).owner.should == self
485
+ end
486
+ X.method(:x).receiver.should == X
487
+ X.x.should == :maybe
488
+ end
489
+
490
+ it "should successfully replace an instance method" do
491
+ pry_eval 'edit -p X#x'
492
+
493
+ X.instance_method(:x).owner.should == X
494
+ X.new.x.should == :maybe
495
+ end
496
+
497
+ it "should successfully replace a method on an instance" do
498
+ pry_eval 'instance = X.new', 'edit -p instance.x'
499
+
500
+ instance = X.new
501
+ instance.method(:x).owner.should == X
502
+ instance.x.should == :maybe
503
+ end
504
+
505
+ it "should successfully replace a method from a module" do
506
+ pry_eval 'edit -p X#a'
507
+
508
+ X.instance_method(:a).owner.should == A
509
+ X.new.a.should == :maybe
510
+ end
511
+
512
+ it "should successfully replace a method with a question mark" do
513
+ pry_eval 'edit -p X#y?'
514
+
515
+ X.instance_method(:y?).owner.should == X
516
+ X.new.y?.should == :maybe
517
+ end
518
+
519
+ it "should preserve module nesting" do
520
+ pry_eval 'edit -p X::B#foo'
521
+
522
+ X::B.instance_method(:foo).owner.should == X::B
523
+ X::B.new.foo.should == :nawt
524
+ end
525
+
526
+ describe "monkey-patching" do
527
+ before do
528
+ @edit = 'edit --patch ' # A shortcut.
529
+ end
530
+
531
+ # @param [Integer] lineno
532
+ # @return [String] the stripped line from the tempfile at +lineno+
533
+ def stripped_line_at(lineno)
534
+ @tempfile.rewind
535
+ @tempfile.lines.to_a[lineno].strip
536
+ end
537
+
538
+ # Applies the monkey patch for +method+ with help of evaluation of
539
+ # +eval_strs+. The idea is to capture the initial line number (before
540
+ # the monkey patch), because it gets overwritten by the line number from
541
+ # the monkey patch. And our goal is to check that the original
542
+ # definition hasn't changed.
543
+ # @param [UnboundMethod] method
544
+ # @param [Array<String>] eval_strs
545
+ # @return [Array<String] the lines with definitions of the same line
546
+ # before monkey patching and after (normally, they should be equal)
547
+ def apply_monkey_patch(method, *eval_strs)
548
+ _, lineno = method.source_location
549
+ definition_before = stripped_line_at(lineno)
550
+
551
+ pry_eval(*eval_strs)
552
+
553
+ definition_after = stripped_line_at(lineno)
554
+
555
+ [definition_before, definition_after]
556
+ end
557
+
558
+ it "should work for a class method" do
559
+ def_before, def_after =
560
+ apply_monkey_patch(X.method(:x), "#@edit X.x")
561
+
562
+ def_before.should == ':double_yup'
563
+ def_after.should == ':double_yup'
564
+ @patched_def.should == ':maybe'
565
+ end
566
+
567
+ it "should work for an instance method" do
568
+ def_before, def_after =
569
+ apply_monkey_patch(X.instance_method(:x), "#@edit X#x")
570
+
571
+ def_before.should == ':nope'
572
+ def_after.should == ':nope'
573
+ @patched_def.should == ':maybe'
574
+ end
575
+
576
+ it "should work for a method on an instance" do
577
+ def_before, def_after =
578
+ apply_monkey_patch(X.instance_method(:x), 'instance = X.new', "#@edit instance.x")
579
+
580
+ def_before.should == ':nope'
581
+ def_after.should == ':nope'
582
+ @patched_def.should == ':maybe'
583
+ end
584
+
585
+ it "should work for a method from a module" do
586
+ def_before, def_after =
587
+ apply_monkey_patch(X.instance_method(:a), "#@edit X#a")
588
+
589
+ def_before.should == ':yup'
590
+ def_after.should == ':yup'
591
+ @patched_def.should == ':maybe'
592
+ end
593
+
594
+ it "should work for a method with a question mark" do
595
+ def_before, def_after =
596
+ apply_monkey_patch(X.instance_method(:y?), "#@edit X#y?")
597
+
598
+ def_before.should == ':because'
599
+ def_after.should == ':because'
600
+ @patched_def.should == ':maybe'
601
+ end
602
+
603
+ it "should work with nesting" do
604
+ def_before, def_after =
605
+ apply_monkey_patch(X::B.instance_method(:foo), "#@edit X::B#foo")
606
+
607
+ def_before.should == ':possibly'
608
+ def_after.should == ':possibly'
609
+ @patched_def.should == ':maybe'
610
+ end
611
+ end
612
+ end
613
+
614
+ describe 'on an aliased method' do
615
+ before do
616
+ Pry.config.editor = lambda do |file, line|
617
+ lines = File.read(file).lines.to_a
618
+ lines[1] = '"#{super}aa".to_sym' + "\n"
619
+ File.open(file, 'w') do |f|
620
+ f.write(lines.join)
621
+ end
622
+ nil
623
+ end
624
+ end
625
+
626
+ it "should change the alias, but not the original, without breaking super" do
627
+
628
+ $x = :bebe
629
+ pry_eval 'edit -p X#c'
630
+
631
+
632
+ Pry::Method.from_str("X#c").alias?.should == true
633
+
634
+ X.new.b.should == :kinda
635
+ X.new.c.should == :kindaaa
636
+ $x = nil
637
+ end
638
+ end
639
+
640
+ describe 'with three-arg editor' do
641
+ before do
642
+ @file = @line = @reloading = nil
643
+ Pry.config.editor = lambda do |file, line, reloading|
644
+ @file = file; @line = line; @reloading = reloading
645
+ nil
646
+ end
647
+ end
648
+
649
+ it "should pass the editor a reloading arg" do
650
+ pry_eval 'edit X.x'
651
+ @reloading.should == true
652
+ pry_eval 'edit -n X.x'
653
+ @reloading.should == false
654
+ end
655
+ end
656
+ end
657
+ end
658
+
659
+ describe "--method flag" do
660
+ before do
661
+ @t = pry_tester
662
+ class BinkyWink
663
+ eval %{
664
+ def tits_macgee
665
+ binding
666
+ end
667
+ }
668
+
669
+ def tots_macgee
670
+ :jeremy_jones
671
+ binding
672
+ end
673
+ end
674
+ end
675
+
676
+ after do
677
+ Object.remove_const(:BinkyWink)
678
+ end
679
+
680
+ it 'should edit method context' do
681
+ Pry.editor = lambda do |file, line|
682
+ [file, line].should == BinkyWink.instance_method(:tots_macgee).source_location
683
+ nil
684
+ end
685
+
686
+ t = pry_tester(BinkyWink.new.tots_macgee)
687
+ t.process_command "edit -m -n"
688
+ end
689
+
690
+ it 'errors when cannot find method context' do
691
+ Pry.editor = lambda do |file, line|
692
+ [file, line].should == BinkyWink.instance_method(:tits_macgee).source_location
693
+ nil
694
+ end
695
+
696
+ t = pry_tester(BinkyWink.new.tits_macgee)
697
+ lambda { t.process_command "edit -m -n" }.should.
698
+ raise(Pry::CommandError).message.should.match(/Cannot find a file for/)
699
+ end
700
+
701
+ it 'errors when a filename arg is passed with --method' do
702
+ lambda { @t.process_command "edit -m Pry#repl" }.should.
703
+ raise(Pry::CommandError).message.should.match(/Only one of/)
704
+ end
705
+ end
706
+
707
+ describe "pretty error messages" do
708
+ before do
709
+ @t = pry_tester
710
+ class TrinkyDink
711
+ eval %{
712
+ def claudia_linklater
713
+ end
714
+ }
715
+ end
716
+ end
717
+
718
+ after do
719
+ Object.remove_const(:TrinkyDink)
720
+ end
721
+
722
+ it 'should display a nice error message when cannot open a file' do
723
+ lambda { @t.process_command "edit TrinkyDink#claudia_linklater" }.should.
724
+ raise(Pry::CommandError).message.should.match(/Cannot find a file for/)
725
+ end
726
+ end
727
+ end