terrapin 0.6.0.alpha

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.
Files changed (41) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +8 -0
  3. data/.travis.yml +6 -0
  4. data/GOALS +8 -0
  5. data/Gemfile +7 -0
  6. data/LICENSE +26 -0
  7. data/NEWS.md +85 -0
  8. data/README.md +215 -0
  9. data/Rakefile +13 -0
  10. data/lib/terrapin.rb +12 -0
  11. data/lib/terrapin/command_line.rb +197 -0
  12. data/lib/terrapin/command_line/multi_pipe.rb +50 -0
  13. data/lib/terrapin/command_line/output.rb +12 -0
  14. data/lib/terrapin/command_line/runners.rb +7 -0
  15. data/lib/terrapin/command_line/runners/backticks_runner.rb +30 -0
  16. data/lib/terrapin/command_line/runners/fake_runner.rb +30 -0
  17. data/lib/terrapin/command_line/runners/popen_runner.rb +29 -0
  18. data/lib/terrapin/command_line/runners/posix_runner.rb +49 -0
  19. data/lib/terrapin/command_line/runners/process_runner.rb +41 -0
  20. data/lib/terrapin/exceptions.rb +8 -0
  21. data/lib/terrapin/os_detector.rb +27 -0
  22. data/lib/terrapin/version.rb +4 -0
  23. data/spec/spec_helper.rb +31 -0
  24. data/spec/support/fake_logger.rb +18 -0
  25. data/spec/support/have_output.rb +11 -0
  26. data/spec/support/nonblocking_examples.rb +14 -0
  27. data/spec/support/stub_os.rb +25 -0
  28. data/spec/support/unsetting_exitstatus.rb +7 -0
  29. data/spec/support/with_exitstatus.rb +12 -0
  30. data/spec/terrapin/command_line/output_spec.rb +14 -0
  31. data/spec/terrapin/command_line/runners/backticks_runner_spec.rb +24 -0
  32. data/spec/terrapin/command_line/runners/fake_runner_spec.rb +22 -0
  33. data/spec/terrapin/command_line/runners/popen_runner_spec.rb +24 -0
  34. data/spec/terrapin/command_line/runners/posix_runner_spec.rb +40 -0
  35. data/spec/terrapin/command_line/runners/process_runner_spec.rb +40 -0
  36. data/spec/terrapin/command_line_spec.rb +195 -0
  37. data/spec/terrapin/errors_spec.rb +62 -0
  38. data/spec/terrapin/os_detector_spec.rb +23 -0
  39. data/spec/terrapin/runners_spec.rb +97 -0
  40. data/terrapin.gemspec +28 -0
  41. metadata +209 -0
@@ -0,0 +1,24 @@
1
+ require 'spec_helper'
2
+
3
+ describe Terrapin::CommandLine::BackticksRunner do
4
+ if Terrapin::CommandLine::BackticksRunner.supported?
5
+ it_behaves_like 'a command that does not block'
6
+
7
+ it 'runs the command given and captures the output in an Output' do
8
+ output = subject.call("echo hello")
9
+ expect(output).to have_output "hello\n"
10
+ end
11
+
12
+ it 'modifies the environment and runs the command given' do
13
+ output = subject.call("echo $yes", {"yes" => "no"})
14
+ expect(output).to have_output "no\n"
15
+ end
16
+
17
+ it 'sets the exitstatus when a command completes' do
18
+ subject.call("ruby -e 'exit 0'")
19
+ $?.exitstatus.should == 0
20
+ subject.call("ruby -e 'exit 5'")
21
+ $?.exitstatus.should == 5
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,22 @@
1
+ require 'spec_helper'
2
+
3
+ describe Terrapin::CommandLine::FakeRunner do
4
+ it 'records commands' do
5
+ subject.call("some command", :environment)
6
+ subject.call("other command", :other_environment)
7
+ subject.commands.should eq [["some command", :environment], ["other command", :other_environment]]
8
+ end
9
+
10
+ it 'can tell if a command was run' do
11
+ subject.call("some command", :environment)
12
+ subject.call("other command", :other_environment)
13
+ subject.ran?("some command").should eq true
14
+ subject.ran?("no command").should eq false
15
+ end
16
+
17
+ it 'can tell if a command was run even if shell options were set' do
18
+ subject.call("something 2>/dev/null", :environment)
19
+ subject.ran?("something").should eq true
20
+ end
21
+
22
+ end
@@ -0,0 +1,24 @@
1
+ require 'spec_helper'
2
+
3
+ describe Terrapin::CommandLine::PopenRunner do
4
+ if Terrapin::CommandLine::PopenRunner.supported?
5
+ it_behaves_like 'a command that does not block'
6
+
7
+ it 'runs the command given and captures the output in an Output' do
8
+ output = subject.call("echo hello")
9
+ expect(output).to have_output "hello\n"
10
+ end
11
+
12
+ it 'modifies the environment and runs the command given' do
13
+ output = subject.call("echo $yes", {"yes" => "no"})
14
+ expect(output).to have_output "no\n"
15
+ end
16
+
17
+ it 'sets the exitstatus when a command completes' do
18
+ subject.call("ruby -e 'exit 0'")
19
+ $?.exitstatus.should == 0
20
+ subject.call("ruby -e 'exit 5'")
21
+ $?.exitstatus.should == 5
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,40 @@
1
+ require 'spec_helper'
2
+
3
+ describe Terrapin::CommandLine::PosixRunner do
4
+ if Terrapin::CommandLine::PosixRunner.supported?
5
+ it_behaves_like 'a command that does not block'
6
+
7
+ it 'runs the command given and captures the output' do
8
+ output = subject.call("echo hello")
9
+ expect(output).to have_output "hello\n"
10
+ end
11
+
12
+ it 'runs the command given and captures the error output' do
13
+ output = subject.call("echo hello 1>&2")
14
+ expect(output).to have_error_output "hello\n"
15
+ end
16
+
17
+ it 'modifies the environment and runs the command given' do
18
+ output = subject.call("echo $yes", {"yes" => "no"})
19
+ expect(output).to have_output "no\n"
20
+ end
21
+
22
+ it 'sets the exitstatus when a command completes' do
23
+ subject.call("ruby -e 'exit 0'")
24
+ $?.exitstatus.should == 0
25
+ subject.call("ruby -e 'exit 5'")
26
+ $?.exitstatus.should == 5
27
+ end
28
+
29
+ it "runs the command it's given and allows access to stderr afterwards" do
30
+ cmd = Terrapin::CommandLine.new(
31
+ "ruby",
32
+ "-e '$stdout.puts %{hello}; $stderr.puts %{goodbye}'",
33
+ :swallow_stderr => false
34
+ )
35
+ cmd.run
36
+ expect(cmd.command_output).to eq "hello\n"
37
+ expect(cmd.command_error_output).to eq "goodbye\n"
38
+ end
39
+ end
40
+ end
@@ -0,0 +1,40 @@
1
+ require 'spec_helper'
2
+
3
+ describe Terrapin::CommandLine::ProcessRunner do
4
+ if Terrapin::CommandLine::ProcessRunner.supported?
5
+ it_behaves_like "a command that does not block"
6
+
7
+ it 'runs the command given and captures the output' do
8
+ output = subject.call("echo hello")
9
+ expect(output).to have_output "hello\n"
10
+ end
11
+
12
+ it 'runs the command given and captures the error output' do
13
+ output = subject.call("echo hello 1>&2")
14
+ expect(output).to have_error_output "hello\n"
15
+ end
16
+
17
+ it 'modifies the environment and runs the command given' do
18
+ output = subject.call("echo $yes", {"yes" => "no"})
19
+ expect(output).to have_output "no\n"
20
+ end
21
+
22
+ it 'sets the exitstatus when a command completes' do
23
+ subject.call("ruby -e 'exit 0'")
24
+ $?.exitstatus.should == 0
25
+ subject.call("ruby -e 'exit 5'")
26
+ $?.exitstatus.should == 5
27
+ end
28
+
29
+ it "runs the command it's given and allows access to stderr afterwards" do
30
+ cmd = Terrapin::CommandLine.new(
31
+ "ruby",
32
+ "-e '$stdout.puts %{hello}; $stderr.puts %{goodbye}'",
33
+ :swallow_stderr => false
34
+ )
35
+ cmd.run
36
+ expect(cmd.command_output).to eq "hello\n"
37
+ expect(cmd.command_error_output).to eq "goodbye\n"
38
+ end
39
+ end
40
+ end
@@ -0,0 +1,195 @@
1
+ require 'spec_helper'
2
+
3
+ describe Terrapin::CommandLine do
4
+ before do
5
+ Terrapin::CommandLine.path = nil
6
+ on_unix! # Assume we're on unix unless otherwise specified.
7
+ end
8
+
9
+ it "takes a command and parameters and produces a Bash command line" do
10
+ cmd = Terrapin::CommandLine.new("convert", "a.jpg b.png", :swallow_stderr => false)
11
+ cmd.command.should == "convert a.jpg b.png"
12
+ end
13
+
14
+ it "specifies the $PATH where the command can be found on unix" do
15
+ Terrapin::CommandLine.path = ["/path/to/command/dir", "/"]
16
+ cmd = Terrapin::CommandLine.new("ls")
17
+ cmd.command.should == "PATH=/path/to/command/dir:/:$PATH; ls"
18
+ end
19
+
20
+ it "specifies the %PATH% where the command can be found on windows" do
21
+ on_windows!
22
+ Terrapin::CommandLine.path = ['C:\system32', 'D:\\']
23
+ cmd = Terrapin::CommandLine.new("dir")
24
+ cmd.command.should == 'SET PATH=C:\system32;D:\;%PATH% & dir'
25
+ end
26
+
27
+ it "specifies more than one path where the command can be found" do
28
+ Terrapin::CommandLine.path = ["/path/to/command/dir", "/some/other/path"]
29
+ cmd = Terrapin::CommandLine.new("ruby", "-e 'puts ENV[%{PATH}]'")
30
+ output = cmd.run
31
+ output.should match(%r{/path/to/command/dir})
32
+ output.should match(%r{/some/other/path})
33
+ end
34
+
35
+ it "temporarily changes specified environment variables" do
36
+ Terrapin::CommandLine.environment['TEST'] = 'Hello, world!'
37
+ cmd = Terrapin::CommandLine.new("ruby", "-e 'puts ENV[%{TEST}]'")
38
+ output = cmd.run
39
+ output.should match(%r{Hello, world!})
40
+ end
41
+
42
+ it 'changes environment variables for the command line' do
43
+ Terrapin::CommandLine.environment['TEST'] = 'Hello, world!'
44
+ cmd = Terrapin::CommandLine.new("ruby",
45
+ "-e 'puts ENV[%{TEST}]'",
46
+ :environment => {'TEST' => 'Hej hej'})
47
+ output = cmd.run
48
+ output.should match(%r{Hej hej})
49
+ end
50
+
51
+ it 'passes the existing environment variables through to the runner' do
52
+ command = Terrapin::CommandLine.new('echo', '$HOME')
53
+ output = command.run
54
+ output.chomp.should_not == ''
55
+ end
56
+
57
+ it "can interpolate quoted variables into the command line's parameters" do
58
+ cmd = Terrapin::CommandLine.new("convert",
59
+ ":one :{two}",
60
+ :swallow_stderr => false)
61
+
62
+ command_string = cmd.command(:one => "a.jpg", :two => "b.png")
63
+ command_string.should == "convert 'a.jpg' 'b.png'"
64
+ end
65
+
66
+ it 'does not over-interpolate in a command line' do
67
+ cmd = Terrapin::CommandLine.new("convert",
68
+ ":hell :{two} :hello",
69
+ :swallow_stderr => false)
70
+
71
+ command_string = cmd.command(:hell => "a.jpg", :two => "b.png", :hello => "c.tiff")
72
+ command_string.should == "convert 'a.jpg' 'b.png' 'c.tiff'"
73
+ end
74
+
75
+ it "interpolates when running a command" do
76
+ command = Terrapin::CommandLine.new("echo", ":hello_world")
77
+ command.run(:hello_world => "Hello, world").should match(/Hello, world/)
78
+ end
79
+
80
+ it "interpolates any Array arguments when running a command" do
81
+ command = Terrapin::CommandLine.new("echo", "Hello :worlds and :dwarfs")
82
+ command.command(:worlds => %w[mercury venus earth], :dwarfs => "pluto").should == "echo Hello 'mercury' 'venus' 'earth' and 'pluto'"
83
+ end
84
+
85
+ it "quotes command line options differently if we're on windows" do
86
+ on_windows!
87
+ cmd = Terrapin::CommandLine.new("convert",
88
+ ":one :{two}",
89
+ :swallow_stderr => false)
90
+ command_string = cmd.command(:one => "a.jpg", :two => "b.png")
91
+ command_string.should == 'convert "a.jpg" "b.png"'
92
+ end
93
+
94
+ it "can quote and interpolate dangerous variables" do
95
+ cmd = Terrapin::CommandLine.new("convert",
96
+ ":one :two",
97
+ :swallow_stderr => false)
98
+ command_string = cmd.command(:one => "`rm -rf`.jpg", :two => "ha'ha.png'")
99
+ command_string.should == "convert '`rm -rf`.jpg' 'ha'\\''ha.png'\\'''"
100
+ end
101
+
102
+ it 'cannot recursively introduce a place where user-supplied commands can run' do
103
+ cmd = Terrapin::CommandLine.new('convert', ':foo :bar')
104
+ cmd.command(:foo => ':bar', :bar => '`rm -rf`').should == 'convert \':bar\' \'`rm -rf`\''
105
+ end
106
+
107
+ it "can quote and interpolate dangerous variables even on windows" do
108
+ on_windows!
109
+ cmd = Terrapin::CommandLine.new("convert",
110
+ ":one :two",
111
+ :swallow_stderr => false)
112
+ command_string = cmd.command(:one => "`rm -rf`.jpg", :two => "ha'ha.png")
113
+ command_string.should == %{convert "`rm -rf`.jpg" "ha'ha.png"}
114
+ end
115
+
116
+ it "quotes blank values into the command line's parameters" do
117
+ cmd = Terrapin::CommandLine.new("curl",
118
+ "-X POST -d :data :url",
119
+ :swallow_stderr => false)
120
+ command_string = cmd.command(:data => "", :url => "http://localhost:9000")
121
+ command_string.should == "curl -X POST -d '' 'http://localhost:9000'"
122
+ end
123
+
124
+ it "allows colons in parameters" do
125
+ cmd = Terrapin::CommandLine.new("convert", "'a.jpg' xc:black 'b.jpg'", :swallow_stderr => false)
126
+ cmd.command.should == "convert 'a.jpg' xc:black 'b.jpg'"
127
+ end
128
+
129
+ it 'handles symbols in user supplied values' do
130
+ cmd = Terrapin::CommandLine.new("echo", ":foo")
131
+ command_string = cmd.command(:foo => :bar)
132
+ command_string.should == "echo 'bar'"
133
+ end
134
+
135
+ it "can redirect stderr to the bit bucket if requested" do
136
+ cmd = Terrapin::CommandLine.new("convert",
137
+ "a.jpg b.png",
138
+ :swallow_stderr => true)
139
+
140
+ cmd.command.should == "convert a.jpg b.png 2>/dev/null"
141
+ end
142
+
143
+ it "can redirect stderr to the bit bucket on windows" do
144
+ on_windows!
145
+ cmd = Terrapin::CommandLine.new("convert",
146
+ "a.jpg b.png",
147
+ :swallow_stderr => true)
148
+
149
+ cmd.command.should == "convert a.jpg b.png 2>NUL"
150
+ end
151
+
152
+ it "runs the command it's given and returns the output" do
153
+ cmd = Terrapin::CommandLine.new("echo", "hello", :swallow_stderr => false)
154
+ expect(cmd.run).to eq "hello\n"
155
+ end
156
+
157
+ it "runs the command it's given and allows access to stdout afterwards" do
158
+ cmd = Terrapin::CommandLine.new("echo", "hello", :swallow_stderr => false)
159
+ cmd.run
160
+ expect(cmd.command_output).to eq "hello\n"
161
+ end
162
+
163
+ it "colorizes the output to a tty" do
164
+ logger = FakeLogger.new(:tty => true)
165
+ Terrapin::CommandLine.new("echo", "'Logging!' :foo", :logger => logger).run(:foo => "bar")
166
+ logger.entries.should include("\e[32mCommand\e[0m :: echo 'Logging!' 'bar'")
167
+ end
168
+
169
+ it 'can still take something that does not respond to tty as a logger' do
170
+ output_buffer = StringIO.new
171
+ logger = best_logger.new(output_buffer)
172
+ logger.should_not respond_to(:tty?)
173
+ Terrapin::CommandLine.new("echo", "'Logging!' :foo", :logger => logger).run(:foo => "bar")
174
+ output_buffer.rewind
175
+ output_buffer.read.should == "Command :: echo 'Logging!' 'bar'\n"
176
+ end
177
+
178
+ it "logs the command to a supplied logger" do
179
+ logger = FakeLogger.new
180
+ Terrapin::CommandLine.new("echo", "'Logging!' :foo", :logger => logger).run(:foo => "bar")
181
+ logger.entries.should include("Command :: echo 'Logging!' 'bar'")
182
+ end
183
+
184
+ it "logs the command to a default logger" do
185
+ Terrapin::CommandLine.logger = FakeLogger.new
186
+ Terrapin::CommandLine.new("echo", "'Logging!'").run
187
+ Terrapin::CommandLine.logger.entries.should include("Command :: echo 'Logging!'")
188
+ end
189
+
190
+ it "is fine if no logger is supplied" do
191
+ Terrapin::CommandLine.logger = nil
192
+ cmd = Terrapin::CommandLine.new("echo", "'Logging!'", :logger => nil)
193
+ lambda { cmd.run }.should_not raise_error
194
+ end
195
+ end
@@ -0,0 +1,62 @@
1
+ require 'spec_helper'
2
+
3
+ describe "When an error happens" do
4
+ it "raises a CommandLineError if the result code command isn't expected" do
5
+ cmd = Terrapin::CommandLine.new("echo", "hello")
6
+ cmd.stubs(:execute)
7
+ with_exitstatus_returning(1) do
8
+ lambda { cmd.run }.should raise_error(Terrapin::CommandLineError)
9
+ end
10
+ end
11
+
12
+ it "does not raise if the result code is expected, even if nonzero" do
13
+ cmd = Terrapin::CommandLine.new("echo", "hello", expected_outcodes: [0, 1])
14
+ cmd.stubs(:execute)
15
+ with_exitstatus_returning(1) do
16
+ lambda { cmd.run }.should_not raise_error
17
+ end
18
+ end
19
+
20
+ it "adds command output to exception message if the result code is nonzero" do
21
+ cmd = Terrapin::CommandLine.new("echo", "hello")
22
+ error_output = "Error 315"
23
+ cmd.
24
+ stubs(:execute).
25
+ returns(Terrapin::CommandLine::Output.new("", error_output))
26
+ with_exitstatus_returning(1) do
27
+ begin
28
+ cmd.run
29
+ rescue Terrapin::ExitStatusError => e
30
+ e.message.should =~ /STDERR:\s+#{error_output}/
31
+ end
32
+ end
33
+ end
34
+
35
+ it 'passes the error message to the exception when command is not found' do
36
+ cmd = Terrapin::CommandLine.new('test', '')
37
+ cmd.stubs(:execute).raises(Errno::ENOENT.new("not found"))
38
+ begin
39
+ cmd.run
40
+ rescue Terrapin::CommandNotFoundError => e
41
+ expect(e.message).to eq 'No such file or directory - not found'
42
+ end
43
+ end
44
+
45
+ it "should keep result code in #exitstatus" do
46
+ cmd = Terrapin::CommandLine.new("convert")
47
+ cmd.stubs(:execute).with("convert").returns(:correct_value)
48
+ with_exitstatus_returning(1) do
49
+ cmd.run rescue nil
50
+ end
51
+ cmd.exit_status.should == 1
52
+ end
53
+
54
+ it "does not blow up if running the command errored before execution" do
55
+ assuming_no_processes_have_been_run
56
+ command = Terrapin::CommandLine.new("echo", ":hello_world")
57
+ command.stubs(:command).raises("An Error")
58
+
59
+ lambda{ command.run }.should raise_error("An Error")
60
+ command.exit_status.should eq 0
61
+ end
62
+ end
@@ -0,0 +1,23 @@
1
+ require 'spec_helper'
2
+
3
+ describe Terrapin::OSDetector do
4
+ it "detects that the system is unix" do
5
+ on_unix!
6
+ Terrapin::OS.should be_unix
7
+ end
8
+
9
+ it "detects that the system is windows" do
10
+ on_windows!
11
+ Terrapin::OS.should be_windows
12
+ end
13
+
14
+ it "detects that the system is windows (mingw)" do
15
+ on_mingw!
16
+ Terrapin::OS.should be_windows
17
+ end
18
+
19
+ it "detects that the current Ruby is on Java" do
20
+ on_java!
21
+ Terrapin::OS.should be_java
22
+ end
23
+ end
@@ -0,0 +1,97 @@
1
+ require 'spec_helper'
2
+
3
+ describe "When picking a Runner" do
4
+ it "uses the BackticksRunner by default" do
5
+ Terrapin::CommandLine::ProcessRunner.stubs(:supported?).returns(false)
6
+ Terrapin::CommandLine::PosixRunner.stubs(:supported?).returns(false)
7
+
8
+ cmd = Terrapin::CommandLine.new("echo", "hello")
9
+
10
+ cmd.runner.class.should == Terrapin::CommandLine::BackticksRunner
11
+ end
12
+
13
+ it "uses the ProcessRunner on 1.9 and it's available" do
14
+ Terrapin::CommandLine::ProcessRunner.stubs(:supported?).returns(true)
15
+ Terrapin::CommandLine::PosixRunner.stubs(:supported?).returns(false)
16
+
17
+ cmd = Terrapin::CommandLine.new("echo", "hello")
18
+ cmd.runner.class.should == Terrapin::CommandLine::ProcessRunner
19
+ end
20
+
21
+ it "uses the PosixRunner if the PosixRunner is available" do
22
+ Terrapin::CommandLine::PosixRunner.stubs(:supported?).returns(true)
23
+
24
+ cmd = Terrapin::CommandLine.new("echo", "hello")
25
+ cmd.runner.class.should == Terrapin::CommandLine::PosixRunner
26
+ end
27
+
28
+ it "uses the BackticksRunner if the PosixRunner is available, but we told it to use Backticks all the time" do
29
+ Terrapin::CommandLine::PosixRunner.stubs(:supported?).returns(true)
30
+ Terrapin::CommandLine.runner = Terrapin::CommandLine::BackticksRunner.new
31
+
32
+ cmd = Terrapin::CommandLine.new("echo", "hello")
33
+ cmd.runner.class.should == Terrapin::CommandLine::BackticksRunner
34
+ end
35
+
36
+ it "uses the BackticksRunner if the PosixRunner is available, but we told it to use Backticks" do
37
+ Terrapin::CommandLine::PosixRunner.stubs(:supported?).returns(true)
38
+
39
+ cmd = Terrapin::CommandLine.new("echo", "hello", :runner => Terrapin::CommandLine::BackticksRunner.new)
40
+ cmd.runner.class.should == Terrapin::CommandLine::BackticksRunner
41
+ end
42
+
43
+ it "can go into 'Fake' mode" do
44
+ Terrapin::CommandLine.fake!
45
+
46
+ cmd = Terrapin::CommandLine.new("echo", "hello")
47
+ cmd.runner.class.should eq Terrapin::CommandLine::FakeRunner
48
+ end
49
+
50
+ it "can turn off Fake mode" do
51
+ Terrapin::CommandLine.fake!
52
+ Terrapin::CommandLine.unfake!
53
+
54
+ cmd = Terrapin::CommandLine.new("echo", "hello")
55
+ cmd.runner.class.should_not eq Terrapin::CommandLine::FakeRunner
56
+ end
57
+
58
+ it "can use a FakeRunner even if not in Fake mode" do
59
+ Terrapin::CommandLine.unfake!
60
+
61
+ cmd = Terrapin::CommandLine.new("echo", "hello", :runner => Terrapin::CommandLine::FakeRunner.new)
62
+ cmd.runner.class.should eq Terrapin::CommandLine::FakeRunner
63
+ end
64
+ end
65
+
66
+ describe 'When running an executable in the supplemental path' do
67
+ before do
68
+ path = Pathname.new(File.dirname(__FILE__)) + '..' + 'support'
69
+ File.open(path + 'ls', 'w'){|f| f.puts "#!/bin/sh\necho overridden-ls\n" }
70
+ FileUtils.chmod(0755, path + 'ls')
71
+ Terrapin::CommandLine.path = path
72
+ end
73
+
74
+ after do
75
+ FileUtils.rm_f("#{Terrapin::CommandLine.path}/ls")
76
+ end
77
+
78
+ [
79
+ Terrapin::CommandLine::BackticksRunner,
80
+ Terrapin::CommandLine::PopenRunner,
81
+ Terrapin::CommandLine::PosixRunner,
82
+ Terrapin::CommandLine::ProcessRunner
83
+ ].each do |runner_class|
84
+ if runner_class.supported?
85
+ describe runner_class do
86
+ describe '#run' do
87
+ it 'finds the correct executable' do
88
+ Terrapin::CommandLine.runner = runner_class.new
89
+ command = Terrapin::CommandLine.new('ls')
90
+ result = command.run
91
+ expect(result.strip).to eq('overridden-ls')
92
+ end
93
+ end
94
+ end
95
+ end
96
+ end
97
+ end