cocaine 0.2.1 → 0.3.0

Sign up to get free protection for your applications and to get access to all the features.
data/.gitignore CHANGED
@@ -1,3 +1,7 @@
1
1
  *.rbc
2
+ .rbx
2
3
  *.gem
3
4
  Gemfile.lock
5
+ *.swp
6
+ *.swo
7
+ .bundle
@@ -2,7 +2,7 @@ rvm:
2
2
  - 1.8.7
3
3
  - 1.9.2
4
4
  - 1.9.3
5
- - rbx
6
- - rbx-2.0
5
+ - rbx-18mode
6
+ - rbx-19mode
7
7
  - ree
8
8
  - jruby
data/GOALS ADDED
@@ -0,0 +1,8 @@
1
+ Cocaine hits 1.0.0 when:
2
+
3
+ [*] It can run command lines across all major unix platforms.
4
+ [*] It can run command lines on Windows.
5
+ [*] It handles quoting.
6
+ [*] It takes advantage of OS-specific functionality to be thread-safe,
7
+ when possible.
8
+ [ ] It has a consistent and functioning API that pleases us.
data/NEWS.md ADDED
@@ -0,0 +1,10 @@
1
+ New for 0.3.0:
2
+
3
+ * Support blank arguments.
4
+ * Add `CommandLine#unix?`.
5
+ * Add `CommandLine#exit_status`.
6
+ * Automatically use `POSIX::Spawn` if available.
7
+ * Add `CommandLine#environment` as a hash of extra `ENV` data..
8
+ * Add `CommandLine#environment=` to set that hash.
9
+ * Add `CommandLine#runner` which produces an object that responds to `#call`.
10
+ * Fix a race condition but only on Ruby 1.9.
data/README.md CHANGED
@@ -1,24 +1,20 @@
1
- # Cocaine
1
+ # Cocaine [![Build Status](https://secure.travis-ci.org/thoughtbot/cocaine.png)](http://travis-ci.org/thoughtbot/cocaine)
2
2
 
3
3
  A small library for doing (command) lines.
4
4
 
5
- ## Feedback
6
-
7
- Question? Idea? Problem? Bug? Something else? Comment? Concern? Like use question marks?
8
-
9
- [GitHub Issues For All!](https://github.com/thoughtbot/cocaine/issues)
5
+ [API reference](http://rubydoc.info/gems/cocaine/)
10
6
 
11
7
  ## Usage
12
8
 
13
- The basic, normal stuff.
9
+ The basic, normal stuff:
14
10
 
15
11
  ```ruby
16
- line = Cocaine::CommandLine.new("command", "some 'crazy' options")
17
- line.command # => "command some 'crazy' options"
18
- output = line.run # => Get you some output!
12
+ line = Cocaine::CommandLine.new("echo", "hello 'world'")
13
+ line.command # => "echo hello 'world'"
14
+ line.run # => "hello world\n"
19
15
  ```
20
16
 
21
- Allowing arguments to be dynamic:
17
+ Interpolated arguments:
22
18
 
23
19
  ```ruby
24
20
  line = Cocaine::CommandLine.new("convert", ":in -scale :resolution :out",
@@ -59,6 +55,17 @@ rescue Cocaine::ExitStatusError => e
59
55
  end
60
56
  ```
61
57
 
58
+ If your command might return something non-zero, and you expect that, it's cool:
59
+
60
+ ```ruby
61
+ line = Cocaine::CommandLine.new("/usr/bin/false", "", :expected_outcodes => [0, 1])
62
+ begin
63
+ line.run
64
+ rescue Cocaine::ExitStatusError => e
65
+ # => You never get here!
66
+ end
67
+ ```
68
+
62
69
  You don't have the command? You get an exception:
63
70
 
64
71
  ```ruby
@@ -82,7 +89,7 @@ You can even give it a bunch of places to look:
82
89
 
83
90
  ```ruby
84
91
  FileUtils.rm("/opt/bin/lolwut")
85
- `echo 'echo Hello' > /usr/local/bin/lolwut`
92
+ File.open('/usr/local/bin/lolwut') {|f| f.write('echo Hello') }
86
93
  Cocaine::CommandLine.path = ["/opt/bin", "/usr/local/bin"]
87
94
  line = Cocaine::CommandLine.new("lolwut")
88
95
  line.run # => prints 'Hello', because it searches the path
@@ -95,17 +102,6 @@ line = Cocaine::CommandLine.new("/opt/bin/lolwut")
95
102
  line.command # => "/opt/bin/lolwut"
96
103
  ```
97
104
 
98
- If your command might return something non-zero, and you expect that, it's cool:
99
-
100
- ```ruby
101
- line = Cocaine::CommandLine.new("/usr/bin/false", "", :expected_outcodes => [0, 1])
102
- begin
103
- line.run
104
- rescue Cocaine::ExitStatusError => e
105
- # => You never get here!
106
- end
107
- ```
108
-
109
105
  You can see what's getting run. The 'Command' part it logs is in green for visibility!
110
106
 
111
107
  ```ruby
@@ -113,13 +109,34 @@ line = Cocaine::CommandLine.new("echo", ":var", :var => "LOL!", :logger => Logge
113
109
  line.run # => Logs this with #info -> Command :: echo 'LOL!'
114
110
  ```
115
111
 
116
- But you don't have to, as you saw above where it doesn't use this. But you CAN log every command!
112
+ Or log every command:
117
113
 
118
114
  ```ruby
119
115
  Cocaine::CommandLine.logger = Logger.new(STDOUT)
120
116
  Cocaine::CommandLine.new("date").run # => Logs this -> Command :: date
121
117
  ```
122
118
 
119
+ ## POSIX Spawn
120
+
121
+ You can potentially increase performance by installing [the posix-spawn
122
+ gem](https://rubygems.org/gems/posix-spawn). This gem can keep your
123
+ application's heap from being copied when forking command line
124
+ processes. For applications with large heaps the gain can be
125
+ significant. To include `posix-spawn`, simply add it to your `Gemfile` or,
126
+ if you don't use bundler, install the gem.
127
+
128
+ ## Feedback
129
+
130
+ *Security* concerns must be privately emailed to
131
+ [security@thoughtbot.com](security@thoughtbot.com).
132
+
133
+ Question? Idea? Problem? Bug? Comment? Concern? Like using question marks?
134
+
135
+ [GitHub Issues For All!](https://github.com/thoughtbot/cocaine/issues)
136
+
123
137
  ## License
124
138
 
125
- Copyright 2011 Jon Yurek and thoughtbot, inc. This is free software, and may be redistributed under the terms specified in the LICENSE file.
139
+ Copyright 2011 Jon Yurek and thoughtbot, inc. This is free software, and
140
+ may be redistributed under the terms specified in the
141
+ [LICENSE](https://github.com/thoughtbot/cocaine/blob/master/LICENSE)
142
+ file.
@@ -20,5 +20,6 @@ Gem::Specification.new do |s|
20
20
  s.add_development_dependency('bourne')
21
21
  s.add_development_dependency('mocha')
22
22
  s.add_development_dependency('rake')
23
+ s.add_development_dependency('posix-spawn')
23
24
  end
24
25
 
@@ -1,5 +1,6 @@
1
1
  require 'rbconfig'
2
2
  require 'cocaine/command_line'
3
+ require 'cocaine/command_line/runners'
3
4
  require 'cocaine/exceptions'
4
5
 
5
6
  module Cocaine
@@ -1,8 +1,33 @@
1
1
  module Cocaine
2
2
  class CommandLine
3
3
  class << self
4
- attr_accessor :path, :logger
4
+ attr_accessor :logger
5
+
6
+ def path
7
+ @supplemental_path
8
+ end
9
+ def path=(supplemental_path)
10
+ @supplemental_path = supplemental_path
11
+ @supplemental_environment ||= {}
12
+ @supplemental_environment['PATH'] = [ENV['PATH'], *supplemental_path].join(File::PATH_SEPARATOR)
13
+ end
14
+
15
+ def posix_spawn_available?
16
+ @posix_spawn_available ||= begin
17
+ require 'posix/spawn'
18
+ true
19
+ rescue LoadError => e
20
+ false
21
+ end
22
+ end
23
+
24
+ def environment
25
+ @supplemental_environment ||= {}
26
+ end
5
27
  end
28
+ @environment = {}
29
+
30
+ attr_reader :exit_status, :runner
6
31
 
7
32
  def initialize(binary, params = "", options = {})
8
33
  @binary = binary.dup
@@ -12,6 +37,7 @@ module Cocaine
12
37
  @swallow_stderr = @options.delete(:swallow_stderr)
13
38
  @expected_outcodes = @options.delete(:expected_outcodes)
14
39
  @expected_outcodes ||= [0]
40
+ @runner = best_runner
15
41
  end
16
42
 
17
43
  def command
@@ -25,12 +51,12 @@ module Cocaine
25
51
  def run
26
52
  output = ''
27
53
  begin
28
- with_modified_path do
29
- @logger.info("\e[32mCommand\e[0m :: #{command}") if @logger
30
- output = self.class.send(:'`', command)
31
- end
54
+ @logger.info("\e[32mCommand\e[0m :: #{command}") if @logger
55
+ output = execute(command)
32
56
  rescue Errno::ENOENT
33
57
  raise Cocaine::CommandNotFoundError
58
+ ensure
59
+ @exit_status = $?.exitstatus
34
60
  end
35
61
  if $?.exitstatus == 127
36
62
  raise Cocaine::CommandNotFoundError
@@ -41,17 +67,20 @@ module Cocaine
41
67
  output
42
68
  end
43
69
 
70
+ def unix?
71
+ (RbConfig::CONFIG['host_os'] =~ /mswin|mingw/).nil?
72
+ end
73
+
44
74
  private
45
75
 
46
- def with_modified_path
47
- begin
48
- saved_path = ENV['PATH']
49
- extra_path = [self.class.path].flatten
50
- ENV['PATH'] = [ENV['PATH'], *extra_path].join(File::PATH_SEPARATOR)
51
- yield
52
- ensure
53
- ENV['PATH'] = saved_path
54
- end
76
+ def execute(command)
77
+ runner.call(command, self.class.environment)
78
+ end
79
+
80
+ def best_runner
81
+ return PosixRunner.new if self.class.posix_spawn_available?
82
+ return ProcessRunner.new if Process.respond_to?(:spawn)
83
+ BackticksRunner.new
55
84
  end
56
85
 
57
86
  def interpolate(pattern, vars)
@@ -78,20 +107,20 @@ module Cocaine
78
107
  end
79
108
 
80
109
  def shell_quote(string)
81
- return "" if string.nil? or string.empty?
82
- if self.class.unix?
83
- string.split("'").map{|m| "'#{m}'" }.join("\\'")
110
+ return "" if string.nil?
111
+ if unix?
112
+ if string.empty?
113
+ "''"
114
+ else
115
+ string.split("'").map{|m| "'#{m}'" }.join("\\'")
116
+ end
84
117
  else
85
118
  %{"#{string}"}
86
119
  end
87
120
  end
88
121
 
89
122
  def bit_bucket
90
- self.class.unix? ? "2>/dev/null" : "2>NUL"
91
- end
92
-
93
- def self.unix?
94
- (RbConfig::CONFIG['host_os'] =~ /mswin|mingw/).nil?
123
+ unix? ? "2>/dev/null" : "2>NUL"
95
124
  end
96
125
  end
97
126
  end
@@ -0,0 +1,3 @@
1
+ require 'cocaine/command_line/runners/backticks_runner'
2
+ require 'cocaine/command_line/runners/process_runner'
3
+ require 'cocaine/command_line/runners/posix_runner'
@@ -0,0 +1,25 @@
1
+ module Cocaine
2
+ class CommandLine
3
+ class BackticksRunner
4
+
5
+ def call(command, env = {})
6
+ with_modified_environment(env) do
7
+ `#{command}`
8
+ end
9
+ end
10
+
11
+ private
12
+
13
+ def with_modified_environment(env)
14
+ begin
15
+ saved_env = ENV.to_hash
16
+ ENV.update(env)
17
+ yield
18
+ ensure
19
+ ENV.update(saved_env)
20
+ end
21
+ end
22
+
23
+ end
24
+ end
25
+ end
@@ -0,0 +1,27 @@
1
+ module Cocaine
2
+ class CommandLine
3
+ class PosixRunner
4
+ if Cocaine::CommandLine.posix_spawn_available?
5
+
6
+ def call(command, env = {})
7
+ input, output = IO.pipe
8
+ pid = spawn(env, command, :out => output)
9
+ waitpid(pid)
10
+ output.close
11
+ input.read
12
+ end
13
+
14
+ private
15
+
16
+ def spawn(*args)
17
+ POSIX::Spawn.spawn(*args)
18
+ end
19
+
20
+ def waitpid(pid)
21
+ Process.waitpid(pid)
22
+ end
23
+
24
+ end
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,28 @@
1
+ module Cocaine
2
+ class CommandLine
3
+ class ProcessRunner
4
+ if Process.respond_to?(:spawn)
5
+
6
+ def call(command, env = {})
7
+ input, output = IO.pipe
8
+ pid = spawn(env, command, :out => output)
9
+ waitpid(pid)
10
+ output.close
11
+ input.read
12
+ end
13
+
14
+ private
15
+
16
+ def spawn(*args)
17
+ Process.spawn(*args)
18
+ end
19
+
20
+ def waitpid(pid)
21
+ Process.waitpid(pid)
22
+ end
23
+
24
+ end
25
+ end
26
+ end
27
+ end
28
+
@@ -1,3 +1,3 @@
1
1
  module Cocaine
2
- VERSION = "0.2.1".freeze
2
+ VERSION = "0.3.0".freeze
3
3
  end
@@ -0,0 +1,18 @@
1
+ require 'spec_helper'
2
+
3
+ describe Cocaine::CommandLine::BackticksRunner do
4
+ it 'runs the command given' do
5
+ subject.call("echo hello").should == "hello\n"
6
+ end
7
+
8
+ it 'modifies the environment and runs the command given' do
9
+ subject.call("echo $yes", {"yes" => "no"}).should == "no\n"
10
+ end
11
+
12
+ it 'sets the exitstatus when a command completes' do
13
+ subject.call("ruby -e 'exit 0'")
14
+ $?.exitstatus.should == 0
15
+ subject.call("ruby -e 'exit 5'")
16
+ $?.exitstatus.should == 5
17
+ end
18
+ end
@@ -0,0 +1,21 @@
1
+ require 'spec_helper'
2
+
3
+ describe Cocaine::CommandLine::PosixRunner do
4
+ if Cocaine::CommandLine::posix_spawn_available?
5
+ it 'runs the command given' do
6
+ subject.call("echo hello").should == "hello\n"
7
+ end
8
+
9
+ it 'modifies the environment and runs the command given' do
10
+ subject.call("echo $yes", {"yes" => "no"}).should == "no\n"
11
+ end
12
+
13
+ it 'sets the exitstatus when a command completes' do
14
+ subject.call("ruby -e 'exit 0'")
15
+ $?.exitstatus.should == 0
16
+ subject.call("ruby -e 'exit 5'")
17
+ $?.exitstatus.should == 5
18
+ end
19
+ end
20
+ end
21
+
@@ -0,0 +1,20 @@
1
+ require 'spec_helper'
2
+
3
+ describe Cocaine::CommandLine::ProcessRunner do
4
+ if Process.respond_to?(:spawn)
5
+ it 'runs the command given' do
6
+ subject.call("echo hello").should == "hello\n"
7
+ end
8
+
9
+ it 'modifies the environment and runs the command given' do
10
+ subject.call("echo $yes", {"yes" => "no"}).should == "no\n"
11
+ end
12
+
13
+ it 'sets the exitstatus when a command completes' do
14
+ subject.call("ruby -e 'exit 0'")
15
+ $?.exitstatus.should == 0
16
+ subject.call("ruby -e 'exit 5'")
17
+ $?.exitstatus.should == 5
18
+ end
19
+ end
20
+ end
@@ -26,6 +26,13 @@ describe Cocaine::CommandLine do
26
26
  output.should match(%r{/path/to/command/dir})
27
27
  output.should match(%r{/some/other/path})
28
28
  end
29
+
30
+ it "temporarily changes specified environment variables" do
31
+ Cocaine::CommandLine.environment['TEST'] = 'Hello, world!'
32
+ cmd = Cocaine::CommandLine.new("ruby", "-e 'puts ENV[%{TEST}]'")
33
+ output = cmd.run
34
+ output.should match(%r{Hello, world!})
35
+ end
29
36
 
30
37
  it "can interpolate quoted variables into the command line's parameters" do
31
38
  cmd = Cocaine::CommandLine.new("convert",
@@ -65,6 +72,15 @@ describe Cocaine::CommandLine do
65
72
  cmd.command.should == %{convert "`rm -rf`.jpg" "ha'ha.png"}
66
73
  end
67
74
 
75
+ it "quotes blank values into the command line's parameters" do
76
+ cmd = Cocaine::CommandLine.new("curl",
77
+ "-X POST -d :data :url",
78
+ :data => "",
79
+ :url => "http://localhost:9000",
80
+ :swallow_stderr => false)
81
+ cmd.command.should == "curl -X POST -d '' 'http://localhost:9000'"
82
+ end
83
+
68
84
  it "allows colons in parameters" do
69
85
  cmd = Cocaine::CommandLine.new("convert", "'a.jpg' xc:black 'b.jpg'", :swallow_stderr => false)
70
86
  cmd.command.should == "convert 'a.jpg' xc:black 'b.jpg'"
@@ -104,7 +120,7 @@ describe Cocaine::CommandLine do
104
120
 
105
121
  it "runs the command it's given and return the output" do
106
122
  cmd = Cocaine::CommandLine.new("convert", "a.jpg b.png", :swallow_stderr => false)
107
- cmd.class.stubs(:"`").with("convert a.jpg b.png").returns(:correct_value)
123
+ cmd.stubs(:execute).with("convert a.jpg b.png").returns(:correct_value)
108
124
  with_exitstatus_returning(0) do
109
125
  cmd.run.should == :correct_value
110
126
  end
@@ -112,7 +128,7 @@ describe Cocaine::CommandLine do
112
128
 
113
129
  it "raises a CommandLineError if the result code from the command isn't expected" do
114
130
  cmd = Cocaine::CommandLine.new("convert", "a.jpg b.png", :swallow_stderr => false)
115
- cmd.class.stubs(:"`").with("convert a.jpg b.png").returns(:correct_value)
131
+ cmd.stubs(:execute).with("convert a.jpg b.png").returns(:correct_value)
116
132
  with_exitstatus_returning(1) do
117
133
  lambda do
118
134
  cmd.run
@@ -125,7 +141,7 @@ describe Cocaine::CommandLine do
125
141
  "a.jpg b.png",
126
142
  :expected_outcodes => [0, 1],
127
143
  :swallow_stderr => false)
128
- cmd.class.stubs(:"`").with("convert a.jpg b.png").returns(:correct_value)
144
+ cmd.stubs(:execute).with("convert a.jpg b.png").returns(:correct_value)
129
145
  with_exitstatus_returning(1) do
130
146
  lambda do
131
147
  cmd.run
@@ -133,18 +149,27 @@ describe Cocaine::CommandLine do
133
149
  end
134
150
  end
135
151
 
152
+ it "should keep result code in #exitstatus" do
153
+ cmd = Cocaine::CommandLine.new("convert")
154
+ cmd.stubs(:execute).with("convert").returns(:correct_value)
155
+ with_exitstatus_returning(1) do
156
+ cmd.run rescue nil
157
+ end
158
+ cmd.exit_status.should == 1
159
+ end
160
+
136
161
  it "detects that the system is unix" do
137
- Cocaine::CommandLine.unix?.should be_true
162
+ Cocaine::CommandLine.new("convert").unix?.should be_true
138
163
  end
139
164
 
140
165
  it "detects that the system is windows" do
141
166
  on_windows!
142
- Cocaine::CommandLine.unix?.should be_false
167
+ Cocaine::CommandLine.new("convert").unix?.should be_false
143
168
  end
144
169
 
145
170
  it "detects that the system is windows (mingw)" do
146
- on_windows!("mingw")
147
- Cocaine::CommandLine.unix?.should be_false
171
+ on_mingw!
172
+ Cocaine::CommandLine.new("convert").unix?.should be_false
148
173
  end
149
174
 
150
175
  it "logs the command to a supplied logger" do
@@ -166,4 +191,29 @@ describe Cocaine::CommandLine do
166
191
  cmd = Cocaine::CommandLine.new("echo", "'Logging!'", :logger => nil)
167
192
  lambda { cmd.run }.should_not raise_error
168
193
  end
194
+
195
+ describe "command execution" do
196
+ it "uses the BackticksRunner by default" do
197
+ Process.stubs(:respond_to?).with(:spawn).returns(false)
198
+ Cocaine::CommandLine.stubs(:posix_spawn_available?).returns(false)
199
+
200
+ cmd = Cocaine::CommandLine.new("echo", "hello")
201
+ cmd.runner.class.should == Cocaine::CommandLine::BackticksRunner
202
+ end
203
+
204
+ it "uses the ProcessRunner on 1.9 and it's available" do
205
+ Process.stubs(:respond_to?).with(:spawn).returns(true)
206
+ Cocaine::CommandLine.stubs(:posix_spawn_available?).returns(false)
207
+
208
+ cmd = Cocaine::CommandLine.new("echo", "hello")
209
+ cmd.runner.class.should == Cocaine::CommandLine::ProcessRunner
210
+ end
211
+
212
+ it "uses the PosixRunner if the posix-spawn gem is available" do
213
+ Cocaine::CommandLine.stubs(:posix_spawn_available?).returns(true)
214
+
215
+ cmd = Cocaine::CommandLine.new("echo", "hello")
216
+ cmd.runner.class.should == Cocaine::CommandLine::PosixRunner
217
+ end
218
+ end
169
219
  end
@@ -1,10 +1,14 @@
1
1
  module StubOS
2
- def on_windows!(host_string = 'mswin')
3
- stub_os(host_string)
2
+ def on_windows!
3
+ stub_os('mswin')
4
4
  end
5
5
 
6
- def on_unix!(host_string = 'darwin11.0.0')
7
- stub_os(host_string)
6
+ def on_unix!
7
+ stub_os('darwin11.0.0')
8
+ end
9
+
10
+ def on_mingw!
11
+ stub_os('mingw')
8
12
  end
9
13
 
10
14
  def stub_os(host_string)
metadata CHANGED
@@ -1,137 +1,154 @@
1
- --- !ruby/object:Gem::Specification
1
+ --- !ruby/object:Gem::Specification
2
2
  name: cocaine
3
- version: !ruby/object:Gem::Version
4
- hash: 21
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.3.0
5
5
  prerelease:
6
- segments:
7
- - 0
8
- - 2
9
- - 1
10
- version: 0.2.1
11
6
  platform: ruby
12
- authors:
7
+ authors:
13
8
  - Jon Yurek
14
9
  autorequire:
15
10
  bindir: bin
16
11
  cert_chain: []
17
-
18
- date: 2011-12-13 00:00:00 Z
19
- dependencies:
20
- - !ruby/object:Gem::Dependency
12
+ date: 2012-08-29 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
21
15
  name: rspec
22
- prerelease: false
23
- requirement: &id001 !ruby/object:Gem::Requirement
16
+ requirement: !ruby/object:Gem::Requirement
24
17
  none: false
25
- requirements:
26
- - - ">="
27
- - !ruby/object:Gem::Version
28
- hash: 3
29
- segments:
30
- - 0
31
- version: "0"
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
21
+ version: '0'
32
22
  type: :development
33
- version_requirements: *id001
34
- - !ruby/object:Gem::Dependency
35
- name: bourne
36
23
  prerelease: false
37
- requirement: &id002 !ruby/object:Gem::Requirement
24
+ version_requirements: !ruby/object:Gem::Requirement
38
25
  none: false
39
- requirements:
40
- - - ">="
41
- - !ruby/object:Gem::Version
42
- hash: 3
43
- segments:
44
- - 0
45
- version: "0"
26
+ requirements:
27
+ - - ! '>='
28
+ - !ruby/object:Gem::Version
29
+ version: '0'
30
+ - !ruby/object:Gem::Dependency
31
+ name: bourne
32
+ requirement: !ruby/object:Gem::Requirement
33
+ none: false
34
+ requirements:
35
+ - - ! '>='
36
+ - !ruby/object:Gem::Version
37
+ version: '0'
46
38
  type: :development
47
- version_requirements: *id002
48
- - !ruby/object:Gem::Dependency
49
- name: mocha
50
39
  prerelease: false
51
- requirement: &id003 !ruby/object:Gem::Requirement
40
+ version_requirements: !ruby/object:Gem::Requirement
52
41
  none: false
53
- requirements:
54
- - - ">="
55
- - !ruby/object:Gem::Version
56
- hash: 3
57
- segments:
58
- - 0
59
- version: "0"
42
+ requirements:
43
+ - - ! '>='
44
+ - !ruby/object:Gem::Version
45
+ version: '0'
46
+ - !ruby/object:Gem::Dependency
47
+ name: mocha
48
+ requirement: !ruby/object:Gem::Requirement
49
+ none: false
50
+ requirements:
51
+ - - ! '>='
52
+ - !ruby/object:Gem::Version
53
+ version: '0'
60
54
  type: :development
61
- version_requirements: *id003
62
- - !ruby/object:Gem::Dependency
55
+ prerelease: false
56
+ version_requirements: !ruby/object:Gem::Requirement
57
+ none: false
58
+ requirements:
59
+ - - ! '>='
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ - !ruby/object:Gem::Dependency
63
63
  name: rake
64
+ requirement: !ruby/object:Gem::Requirement
65
+ none: false
66
+ requirements:
67
+ - - ! '>='
68
+ - !ruby/object:Gem::Version
69
+ version: '0'
70
+ type: :development
64
71
  prerelease: false
65
- requirement: &id004 !ruby/object:Gem::Requirement
72
+ version_requirements: !ruby/object:Gem::Requirement
73
+ none: false
74
+ requirements:
75
+ - - ! '>='
76
+ - !ruby/object:Gem::Version
77
+ version: '0'
78
+ - !ruby/object:Gem::Dependency
79
+ name: posix-spawn
80
+ requirement: !ruby/object:Gem::Requirement
66
81
  none: false
67
- requirements:
68
- - - ">="
69
- - !ruby/object:Gem::Version
70
- hash: 3
71
- segments:
72
- - 0
73
- version: "0"
82
+ requirements:
83
+ - - ! '>='
84
+ - !ruby/object:Gem::Version
85
+ version: '0'
74
86
  type: :development
75
- version_requirements: *id004
87
+ prerelease: false
88
+ version_requirements: !ruby/object:Gem::Requirement
89
+ none: false
90
+ requirements:
91
+ - - ! '>='
92
+ - !ruby/object:Gem::Version
93
+ version: '0'
76
94
  description: A small library for doing (command) lines
77
95
  email: jyurek@thoughtbot.com
78
96
  executables: []
79
-
80
97
  extensions: []
81
-
82
98
  extra_rdoc_files: []
83
-
84
- files:
99
+ files:
85
100
  - .gitignore
86
101
  - .travis.yml
102
+ - GOALS
87
103
  - Gemfile
88
104
  - LICENSE
105
+ - NEWS.md
89
106
  - README.md
90
107
  - Rakefile
91
108
  - cocaine.gemspec
92
109
  - lib/cocaine.rb
93
110
  - lib/cocaine/command_line.rb
111
+ - lib/cocaine/command_line/runners.rb
112
+ - lib/cocaine/command_line/runners/backticks_runner.rb
113
+ - lib/cocaine/command_line/runners/posix_runner.rb
114
+ - lib/cocaine/command_line/runners/process_runner.rb
94
115
  - lib/cocaine/exceptions.rb
95
116
  - lib/cocaine/version.rb
117
+ - spec/cocaine/command_line/runners/backticks_runner_spec.rb
118
+ - spec/cocaine/command_line/runners/posix_runner_spec.rb
119
+ - spec/cocaine/command_line/runners/process_runner_spec.rb
96
120
  - spec/cocaine/command_line_spec.rb
97
121
  - spec/spec_helper.rb
98
122
  - spec/support/stub_os.rb
99
123
  - spec/support/with_exitstatus.rb
100
124
  homepage: http://www.thoughtbot.com/projects/cocaine
101
125
  licenses: []
102
-
103
126
  post_install_message:
104
127
  rdoc_options: []
105
-
106
- require_paths:
128
+ require_paths:
107
129
  - lib
108
- required_ruby_version: !ruby/object:Gem::Requirement
130
+ required_ruby_version: !ruby/object:Gem::Requirement
109
131
  none: false
110
- requirements:
111
- - - ">="
112
- - !ruby/object:Gem::Version
113
- hash: 3
114
- segments:
132
+ requirements:
133
+ - - ! '>='
134
+ - !ruby/object:Gem::Version
135
+ version: '0'
136
+ segments:
115
137
  - 0
116
- version: "0"
117
- required_rubygems_version: !ruby/object:Gem::Requirement
138
+ hash: 2124621343266974199
139
+ required_rubygems_version: !ruby/object:Gem::Requirement
118
140
  none: false
119
- requirements:
120
- - - ">="
121
- - !ruby/object:Gem::Version
122
- hash: 3
123
- segments:
141
+ requirements:
142
+ - - ! '>='
143
+ - !ruby/object:Gem::Version
144
+ version: '0'
145
+ segments:
124
146
  - 0
125
- version: "0"
147
+ hash: 2124621343266974199
126
148
  requirements: []
127
-
128
149
  rubyforge_project:
129
- rubygems_version: 1.8.6
150
+ rubygems_version: 1.8.24
130
151
  signing_key:
131
152
  specification_version: 3
132
153
  summary: A small library for doing (command) lines
133
- test_files:
134
- - spec/cocaine/command_line_spec.rb
135
- - spec/spec_helper.rb
136
- - spec/support/stub_os.rb
137
- - spec/support/with_exitstatus.rb
154
+ test_files: []