1
0
Fork 0
mirror of https://github.com/pry/pry.git synced 2022-11-09 12:35:05 -05:00

Create PryTester abstraction

This commit is contained in:
Ryan Fitzgerald 2012-07-24 04:36:53 -04:00
parent 8a19a1996f
commit 544ae03620
2 changed files with 132 additions and 126 deletions

View file

@ -203,6 +203,34 @@ ensure
file.close(true) if file file.close(true) if file
end end
def pry_tester(context = nil, &block)
PryTester.new(context).tap do |t|
(class << t; self; end).class_eval(&block)
end
end
class PryTester
attr_reader :pry
def initialize(context)
@pry = Pry.new
if context
@pry.binding_stack << Pry.binding_for(context)
end
end
def eval(*strs)
strs.flatten.map do |str|
if @pry.process_command(str)
result = Thread.current[:__pry_cmd_result__]
result.retval if result
else
@pry.evaluate_ruby(str)
end
end.last
end
end
CommandTester = Pry::CommandSet.new do CommandTester = Pry::CommandSet.new do
command "command1", "command 1 test" do command "command1", "command 1 test" do

View file

@ -1,53 +1,34 @@
require 'helper' require 'helper'
module CdTestHelpers
def binding_stack
evaluate_ruby '_pry_.binding_stack.dup'
end
def assert_binding_stack(other)
binding_stack.map { |b| b.eval('self') }.should == other
end
def command_state
evaluate_ruby '_pry_.command_state["cd"]'
end
def old_stack
evaluate_ruby '_pry_.command_state["cd"].old_stack.dup'
end
def evaluate_self
evaluate_ruby 'self'
end
def process_commands(*args)
args.flatten.each do |cmd|
@pry.process_command cmd
end
end
def evaluate_ruby(ruby)
@pry.evaluate_ruby ruby
end
end
describe 'Pry::DefaultCommands::Cd' do describe 'Pry::DefaultCommands::Cd' do
before do before do
extend CdTestHelpers
@o, @obj = Object.new, Object.new @o, @obj = Object.new, Object.new
@obj.instance_variable_set(:@x, 66) @obj.instance_variable_set(:@x, 66)
@obj.instance_variable_set(:@y, 79) @obj.instance_variable_set(:@y, 79)
@o.instance_variable_set(:@obj, @obj) @o.instance_variable_set(:@obj, @obj)
@pry = Pry.new @t = pry_tester(@o) do
@pry.binding_stack << Pry.binding_for(@o) def assert_binding_stack(other)
binding_stack.map { |b| b.eval('self') }.should == other
end
def binding_stack
eval '_pry_.binding_stack.dup'
end
def command_state
eval '_pry_.command_state["cd"]'
end
def old_stack
eval '_pry_.command_state["cd"].old_stack.dup'
end
end
end end
describe 'state' do describe 'state' do
it 'should not to be set up in fresh instance' do it 'should not to be set up in fresh instance' do
command_state.should.be.nil @t.command_state.should.be.nil
end end
end end
@ -55,8 +36,8 @@ describe 'Pry::DefaultCommands::Cd' do
describe 'in fresh pry instance' do describe 'in fresh pry instance' do
it 'should not toggle when there is no old stack' do it 'should not toggle when there is no old stack' do
2.times do 2.times do
process_commands 'cd -' @t.eval 'cd -'
assert_binding_stack [@o] @t.assert_binding_stack [@o]
end end
end end
end end
@ -64,185 +45,182 @@ describe 'Pry::DefaultCommands::Cd' do
describe 'when an error was raised' do describe 'when an error was raised' do
it 'should not toggle and should keep correct stacks' do it 'should not toggle and should keep correct stacks' do
proc { proc {
process_commands 'cd @' @t.eval 'cd @'
}.should.raise(Pry::CommandError) }.should.raise(Pry::CommandError)
old_stack.should == [] @t.old_stack.should == []
assert_binding_stack [@o] @t.assert_binding_stack [@o]
process_commands 'cd -' @t.eval 'cd -'
old_stack.should == [] @t.old_stack.should == []
assert_binding_stack [@o] @t.assert_binding_stack [@o]
end end
end end
describe 'when using simple cd syntax' do describe 'when using simple cd syntax' do
it 'should toggle' do it 'should toggle' do
process_commands 'cd :mon_dogg', 'cd -' @t.eval 'cd :mon_dogg', 'cd -'
assert_binding_stack [@o] @t.assert_binding_stack [@o]
process_commands 'cd -' @t.eval 'cd -'
assert_binding_stack [@o, :mon_dogg] @t.assert_binding_stack [@o, :mon_dogg]
end end
end end
describe "when using complex cd syntax" do describe "when using complex cd syntax" do
it 'should toggle with a complex path (simple case)' do it 'should toggle with a complex path (simple case)' do
process_commands 'cd 1/2/3', 'cd -' @t.eval 'cd 1/2/3', 'cd -'
assert_binding_stack [@o] @t.assert_binding_stack [@o]
process_commands 'cd -' @t.eval 'cd -'
assert_binding_stack [@o, 1, 2, 3] @t.assert_binding_stack [@o, 1, 2, 3]
end end
it 'should toggle with a complex path (more complex case)' do it 'should toggle with a complex path (more complex case)' do
process_commands 'cd 1/2/3', 'cd ../4', 'cd -' @t.eval 'cd 1/2/3', 'cd ../4', 'cd -'
assert_binding_stack [@o, 1, 2, 3] @t.assert_binding_stack [@o, 1, 2, 3]
process_commands 'cd -' @t.eval 'cd -'
assert_binding_stack [@o, 1, 2, 4] @t.assert_binding_stack [@o, 1, 2, 4]
end end
end end
describe 'series of cd calls' do describe 'series of cd calls' do
it 'should toggle with fuzzy `cd -` calls' do it 'should toggle with fuzzy `cd -` calls' do
process_commands 'cd :mon_dogg', 'cd -', 'cd 42', 'cd -' @t.eval 'cd :mon_dogg', 'cd -', 'cd 42', 'cd -'
assert_binding_stack [@o] @t.assert_binding_stack [@o]
process_commands 'cd -' @t.eval 'cd -'
assert_binding_stack [@o, 42] @t.assert_binding_stack [@o, 42]
end end
end end
describe 'when using cd ..' do describe 'when using cd ..' do
it 'should toggle with a simple path' do it 'should toggle with a simple path' do
process_commands 'cd :john_dogg', 'cd ..' @t.eval 'cd :john_dogg', 'cd ..'
assert_binding_stack [@o] @t.assert_binding_stack [@o]
process_commands 'cd -' @t.eval 'cd -'
assert_binding_stack [@o, :john_dogg] @t.assert_binding_stack [@o, :john_dogg]
end end
it 'should toggle with a complex path' do it 'should toggle with a complex path' do
process_commands 'cd 1/2/3/../4', 'cd -' @t.eval 'cd 1/2/3/../4', 'cd -'
assert_binding_stack [@o] @t.assert_binding_stack [@o]
process_commands 'cd -' @t.eval 'cd -'
assert_binding_stack [@o, 1, 2, 4] @t.assert_binding_stack [@o, 1, 2, 4]
end end
end end
describe 'when using cd ::' do describe 'when using cd ::' do
it 'should toggle' do it 'should toggle' do
process_commands 'cd ::', 'cd -' @t.eval 'cd ::', 'cd -'
assert_binding_stack [@o] @t.assert_binding_stack [@o]
process_commands 'cd -' @t.eval 'cd -'
assert_binding_stack [@o, TOPLEVEL_BINDING.eval('self')] @t.assert_binding_stack [@o, TOPLEVEL_BINDING.eval('self')]
end end
end end
describe 'when using cd /' do describe 'when using cd /' do
it 'should toggle' do it 'should toggle' do
process_commands 'cd /', 'cd -' @t.eval 'cd /', 'cd -'
assert_binding_stack [@o] @t.assert_binding_stack [@o]
process_commands 'cd :john_dogg', 'cd /', 'cd -' @t.eval 'cd :john_dogg', 'cd /', 'cd -'
assert_binding_stack [@o, :john_dogg] @t.assert_binding_stack [@o, :john_dogg]
end end
end end
describe 'when using ^D (Control-D) key press' do describe 'when using ^D (Control-D) key press' do
it 'should keep correct old binding' do it 'should keep correct old binding' do
process_commands 'cd :john_dogg', 'cd :mon_dogg', 'cd :kyr_dogg' @t.eval 'cd :john_dogg', 'cd :mon_dogg', 'cd :kyr_dogg',
evaluate_ruby 'Pry::DEFAULT_CONTROL_D_HANDLER.call("", _pry_)' 'Pry::DEFAULT_CONTROL_D_HANDLER.call("", _pry_)'
assert_binding_stack [@o, :john_dogg, :mon_dogg] @t.assert_binding_stack [@o, :john_dogg, :mon_dogg]
process_commands 'cd -' @t.eval 'cd -'
assert_binding_stack [@o, :john_dogg, :mon_dogg, :kyr_dogg] @t.assert_binding_stack [@o, :john_dogg, :mon_dogg, :kyr_dogg]
process_commands 'cd -' @t.eval 'cd -'
assert_binding_stack [@o, :john_dogg, :mon_dogg] @t.assert_binding_stack [@o, :john_dogg, :mon_dogg]
end end
end end
end end
it 'should cd into simple input' do it 'should cd into simple input' do
process_commands 'cd :mon_ouie' @t.eval 'cd :mon_ouie'
evaluate_self.should == :mon_ouie @t.eval('self').should == :mon_ouie
end end
it 'should break out of session with cd ..' do it 'should break out of session with cd ..' do
process_commands 'cd :outer', 'cd :inner' @t.eval 'cd :outer', 'cd :inner'
evaluate_self.should == :inner @t.eval('self').should == :inner
process_commands 'cd ..' @t.eval 'cd ..'
evaluate_self.should == :outer @t.eval('self').should == :outer
end end
it "should not leave the REPL session when given 'cd ..'" do it "should not leave the REPL session when given 'cd ..'" do
process_commands 'cd ..' @t.eval 'cd ..'
evaluate_self.should == @o @t.eval('self').should == @o
end end
it 'should break out to outer-most session with cd /' do it 'should break out to outer-most session with cd /' do
process_commands 'cd :inner' @t.eval 'cd :inner'
evaluate_self.should == :inner @t.eval('self').should == :inner
process_commands 'cd 5' @t.eval 'cd 5'
evaluate_self.should == 5 @t.eval('self').should == 5
process_commands 'cd /' @t.eval 'cd /'
evaluate_self.should == @o @t.eval('self').should == @o
end end
it 'should break out to outer-most session with just cd (no args)' do it 'should break out to outer-most session with just cd (no args)' do
process_commands 'cd :inner' @t.eval 'cd :inner'
evaluate_self.should == :inner @t.eval('self').should == :inner
process_commands 'cd 5' @t.eval 'cd 5'
evaluate_self.should == 5 @t.eval('self').should == 5
process_commands 'cd' @t.eval 'cd'
evaluate_self.should == @o @t.eval('self').should == @o
end end
it 'should cd into an object and its ivar using cd obj/@ivar syntax' do it 'should cd into an object and its ivar using cd obj/@ivar syntax' do
process_commands 'cd @obj/@x' @t.eval 'cd @obj/@x'
assert_binding_stack [@o, @obj, 66] @t.assert_binding_stack [@o, @obj, 66]
end end
it 'should cd into an object and its ivar using cd obj/@ivar/ syntax (note following /)' do it 'should cd into an object and its ivar using cd obj/@ivar/ syntax (note following /)' do
process_commands 'cd @obj/@x/' @t.eval 'cd @obj/@x/'
assert_binding_stack [@o, @obj, 66] @t.assert_binding_stack [@o, @obj, 66]
end end
it 'should cd into previous object and its local using cd ../local syntax' do it 'should cd into previous object and its local using cd ../local syntax' do
process_commands 'cd @obj' @t.eval 'cd @obj', 'local = :local', 'cd @x', 'cd ../local'
evaluate_ruby 'local = :local' @t.assert_binding_stack [@o, @obj, :local]
process_commands 'cd @x', 'cd ../local'
assert_binding_stack [@o, @obj, :local]
end end
it 'should cd into an object and its ivar and back again using cd obj/@ivar/.. syntax' do it 'should cd into an object and its ivar and back again using cd obj/@ivar/.. syntax' do
process_commands 'cd @obj/@x/..' @t.eval 'cd @obj/@x/..'
assert_binding_stack [@o, @obj] @t.assert_binding_stack [@o, @obj]
end end
it 'should cd into an object and its ivar and back and then into another ivar using cd obj/@ivar/../@y syntax' do it 'should cd into an object and its ivar and back and then into another ivar using cd obj/@ivar/../@y syntax' do
process_commands 'cd @obj/@x/../@y' @t.eval 'cd @obj/@x/../@y'
assert_binding_stack [@o, @obj, 79] @t.assert_binding_stack [@o, @obj, 79]
end end
it 'should cd back to top-level and then into another ivar using cd /@ivar/ syntax' do it 'should cd back to top-level and then into another ivar using cd /@ivar/ syntax' do
evaluate_ruby '@z = 20' @t.eval '@z = 20', 'cd @obj/@x/', 'cd /@z'
process_commands 'cd @obj/@x/', 'cd /@z' @t.assert_binding_stack [@o, 20]
assert_binding_stack [@o, 20]
end end
it 'should start a session on TOPLEVEL_BINDING with cd ::' do it 'should start a session on TOPLEVEL_BINDING with cd ::' do
process_commands 'cd ::' @t.eval 'cd ::'
evaluate_self.should == TOPLEVEL_BINDING.eval('self') @t.eval('self').should == TOPLEVEL_BINDING.eval('self')
end end
it 'should cd into complex input (with spaces)' do it 'should cd into complex input (with spaces)' do
@ -250,23 +228,23 @@ describe 'Pry::DefaultCommands::Cd' do
:mon_ouie :mon_ouie
end end
process_commands 'cd hello 1, 2, 3' @t.eval 'cd hello 1, 2, 3'
evaluate_self.should == :mon_ouie @t.eval('self').should == :mon_ouie
end end
it 'should not cd into complex input when it encounters an exception' do it 'should not cd into complex input when it encounters an exception' do
proc { proc {
process_commands 'cd 1/2/swoop_a_doop/3' @t.eval 'cd 1/2/swoop_a_doop/3'
}.should.raise(Pry::CommandError) }.should.raise(Pry::CommandError)
assert_binding_stack [@o] @t.assert_binding_stack [@o]
end end
# Regression test for ticket #516. # Regression test for ticket #516.
# FIXME: This is actually broken. # FIXME: This is actually broken.
# it 'should be able to cd into the Object BasicObject' do # it 'should be able to cd into the Object BasicObject' do
# proc { # proc {
# process_commands 'cd BasicObject.new' # @t.eval 'cd BasicObject.new'
# }.should.not.raise # }.should.not.raise
# end # end
end end