childprocess 0.1.6 → 0.1.7
Sign up to get free protection for your applications and to get access to all the features.
- data/LICENSE +1 -1
- data/README.rdoc +1 -2
- data/VERSION +1 -1
- data/childprocess.gemspec +5 -4
- data/lib/childprocess.rb +8 -0
- data/lib/childprocess/abstract_process.rb +6 -2
- data/lib/childprocess/jruby/process.rb +20 -0
- data/lib/childprocess/unix/process.rb +5 -1
- data/lib/childprocess/windows/process.rb +4 -0
- data/spec/childprocess_spec.rb +2 -2
- data/spec/jruby_spec.rb +13 -1
- data/spec/pid_behavior.rb +13 -0
- data/spec/spec_helper.rb +13 -4
- data/spec/unix_spec.rb +4 -1
- data/spec/windows_spec.rb +4 -1
- metadata +6 -22
data/LICENSE
CHANGED
data/README.rdoc
CHANGED
@@ -18,7 +18,6 @@ a standalone library.
|
|
18
18
|
|
19
19
|
process.start
|
20
20
|
|
21
|
-
process.started? #=> true
|
22
21
|
process.alive? #=> true
|
23
22
|
process.exited? #=> false
|
24
23
|
|
@@ -48,4 +47,4 @@ How the process is launched and killed depends on the platform:
|
|
48
47
|
|
49
48
|
== Copyright
|
50
49
|
|
51
|
-
Copyright (c) 2010 Jari Bakken. See LICENSE for details.
|
50
|
+
Copyright (c) 2010-2011 Jari Bakken. See LICENSE for details.
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.1.
|
1
|
+
0.1.7
|
data/childprocess.gemspec
CHANGED
@@ -5,11 +5,11 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = %q{childprocess}
|
8
|
-
s.version = "0.1.
|
8
|
+
s.version = "0.1.7"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["Jari Bakken"]
|
12
|
-
s.date = %q{
|
12
|
+
s.date = %q{2011-02-12}
|
13
13
|
s.description = %q{This gem aims at being a simple and reliable solution for controlling external programs running in the background on any Ruby / OS combination.}
|
14
14
|
s.email = %q{jari.bakken@gmail.com}
|
15
15
|
s.extra_rdoc_files = [
|
@@ -48,25 +48,26 @@ Gem::Specification.new do |s|
|
|
48
48
|
"spec/abstract_io_spec.rb",
|
49
49
|
"spec/childprocess_spec.rb",
|
50
50
|
"spec/jruby_spec.rb",
|
51
|
+
"spec/pid_behavior.rb",
|
51
52
|
"spec/spec_helper.rb",
|
52
53
|
"spec/unix_spec.rb",
|
53
54
|
"spec/windows_spec.rb"
|
54
55
|
]
|
55
56
|
s.homepage = %q{http://github.com/jarib/childprocess}
|
56
57
|
s.require_paths = ["lib"]
|
57
|
-
s.rubygems_version = %q{1.
|
58
|
+
s.rubygems_version = %q{1.5.0}
|
58
59
|
s.summary = %q{Cross-platform ruby library for managing child processes.}
|
59
60
|
s.test_files = [
|
60
61
|
"spec/abstract_io_spec.rb",
|
61
62
|
"spec/childprocess_spec.rb",
|
62
63
|
"spec/jruby_spec.rb",
|
64
|
+
"spec/pid_behavior.rb",
|
63
65
|
"spec/spec_helper.rb",
|
64
66
|
"spec/unix_spec.rb",
|
65
67
|
"spec/windows_spec.rb"
|
66
68
|
]
|
67
69
|
|
68
70
|
if s.respond_to? :specification_version then
|
69
|
-
current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
|
70
71
|
s.specification_version = 3
|
71
72
|
|
72
73
|
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
data/lib/childprocess.rb
CHANGED
@@ -49,6 +49,14 @@ module ChildProcess
|
|
49
49
|
platform == :jruby
|
50
50
|
end
|
51
51
|
|
52
|
+
def jruby_on_unix?
|
53
|
+
return false unless jruby?
|
54
|
+
# patterns grabbed from http://lopica.sourceforge.net/os.html
|
55
|
+
require "java"
|
56
|
+
name = java.lang.System.getProperty("os.name").downcase
|
57
|
+
name =~ /mac os|linux|solaris|bsd/
|
58
|
+
end
|
59
|
+
|
52
60
|
def windows?
|
53
61
|
!jruby? && os == :windows
|
54
62
|
end
|
@@ -1,5 +1,7 @@
|
|
1
1
|
module ChildProcess
|
2
2
|
class AbstractProcess
|
3
|
+
POLL_INTERVAL = 0.1
|
4
|
+
|
3
5
|
attr_reader :exit_code
|
4
6
|
|
5
7
|
#
|
@@ -35,6 +37,10 @@ module ChildProcess
|
|
35
37
|
raise SubclassResponsibility, "io"
|
36
38
|
end
|
37
39
|
|
40
|
+
def pid
|
41
|
+
raise SubclassResponsibility, "pid"
|
42
|
+
end
|
43
|
+
|
38
44
|
#
|
39
45
|
# Launch the child process
|
40
46
|
#
|
@@ -112,8 +118,6 @@ module ChildProcess
|
|
112
118
|
raise SubclassResponsibility, "launch_process"
|
113
119
|
end
|
114
120
|
|
115
|
-
POLL_INTERVAL = 0.1
|
116
|
-
|
117
121
|
def started?
|
118
122
|
@started
|
119
123
|
end
|
@@ -28,6 +28,26 @@ module ChildProcess
|
|
28
28
|
@exit_code = @process.exitValue
|
29
29
|
end
|
30
30
|
|
31
|
+
#
|
32
|
+
# Only supported in JRuby on a Unix operating system, thanks to limitations
|
33
|
+
# in Java's classes
|
34
|
+
#
|
35
|
+
# @return [Fixnum] the pid of the process after it has started
|
36
|
+
# @raise [NotImplementedError] when trying to access pid on non-Unix platform
|
37
|
+
#
|
38
|
+
def pid
|
39
|
+
if @process.getClass.getName != "java.lang.UNIXProcess"
|
40
|
+
raise NotImplementedError.new("pid is not supported by JRuby child processes on Windows")
|
41
|
+
end
|
42
|
+
|
43
|
+
# About the best way we can do this is with a nasty reflection-based impl
|
44
|
+
# Thanks to Martijn Courteaux
|
45
|
+
# http://stackoverflow.com/questions/2950338/how-can-i-kill-a-linux-process-in-java-with-sigkill-process-destroy-does-sigter/2951193#2951193
|
46
|
+
field = @process.getClass.getDeclaredField("pid")
|
47
|
+
field.accessible = true
|
48
|
+
field.get(@process)
|
49
|
+
end
|
50
|
+
|
31
51
|
private
|
32
52
|
|
33
53
|
def launch_process(&blk)
|
@@ -1,6 +1,10 @@
|
|
1
1
|
module ChildProcess
|
2
2
|
module Unix
|
3
3
|
class Process < AbstractProcess
|
4
|
+
#
|
5
|
+
# @return [Fixnum] the pid of the process after it has started
|
6
|
+
#
|
7
|
+
attr_reader :pid
|
4
8
|
|
5
9
|
def io
|
6
10
|
@io ||= Unix::IO.new
|
@@ -19,7 +23,7 @@ module ChildProcess
|
|
19
23
|
send_kill
|
20
24
|
wait
|
21
25
|
rescue Errno::ECHILD, Errno::ESRCH
|
22
|
-
# handle
|
26
|
+
# handle race condition where process dies between timeout
|
23
27
|
# and send_kill
|
24
28
|
true
|
25
29
|
end
|
data/spec/childprocess_spec.rb
CHANGED
@@ -39,14 +39,14 @@ describe ChildProcess do
|
|
39
39
|
|
40
40
|
it "lets child process inherit the environment of the current process" do
|
41
41
|
Tempfile.open("env-spec") do |file|
|
42
|
-
with_env('
|
42
|
+
with_env('INHERITED' => 'yes') do
|
43
43
|
process = write_env(file.path).start
|
44
44
|
process.poll_for_exit(EXIT_TIMEOUT)
|
45
45
|
end
|
46
46
|
|
47
47
|
file.rewind
|
48
48
|
child_env = eval(file.read)
|
49
|
-
child_env['
|
49
|
+
child_env['INHERITED'].should == 'yes'
|
50
50
|
end
|
51
51
|
end
|
52
52
|
|
data/spec/jruby_spec.rb
CHANGED
@@ -1,4 +1,5 @@
|
|
1
1
|
require File.expand_path('../spec_helper', __FILE__)
|
2
|
+
require "pid_behavior"
|
2
3
|
|
3
4
|
if ChildProcess.jruby?
|
4
5
|
describe ChildProcess::JRuby::IO do
|
@@ -9,4 +10,15 @@ if ChildProcess.jruby?
|
|
9
10
|
end
|
10
11
|
end
|
11
12
|
|
12
|
-
|
13
|
+
describe ChildProcess::JRuby::Process do
|
14
|
+
if ChildProcess.jruby_on_unix?
|
15
|
+
it_behaves_like "a platform that provides the child's pid"
|
16
|
+
else
|
17
|
+
it "raises an error when trying to access the child's pid" do
|
18
|
+
process = exit_with(0)
|
19
|
+
process.start
|
20
|
+
lambda { process.pid }.should raise_error(NotImplementedError)
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
@@ -0,0 +1,13 @@
|
|
1
|
+
require File.expand_path('../spec_helper', __FILE__)
|
2
|
+
|
3
|
+
shared_examples_for "a platform that provides the child's pid" do
|
4
|
+
it "knows the child's pid" do
|
5
|
+
Tempfile.open("pid-spec") do |file|
|
6
|
+
process = write_pid(file.path)
|
7
|
+
process.start
|
8
|
+
process.poll_for_exit(10)
|
9
|
+
file.rewind
|
10
|
+
process.pid.should == file.read.chomp.to_i
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
data/spec/spec_helper.rb
CHANGED
@@ -43,6 +43,14 @@ module ChildProcessSpecHelper
|
|
43
43
|
ruby_process(tmp_script(code), *args)
|
44
44
|
end
|
45
45
|
|
46
|
+
def write_pid(path)
|
47
|
+
code = <<-RUBY
|
48
|
+
File.open(#{path.inspect}, "w") { |f| f << Process.pid }
|
49
|
+
RUBY
|
50
|
+
|
51
|
+
ruby_process tmp_script(code)
|
52
|
+
end
|
53
|
+
|
46
54
|
def exit_with(exit_code)
|
47
55
|
ruby_process(tmp_script("exit(#{exit_code})"))
|
48
56
|
end
|
@@ -57,13 +65,14 @@ module ChildProcessSpecHelper
|
|
57
65
|
end
|
58
66
|
|
59
67
|
def tmp_script(code)
|
60
|
-
|
61
|
-
tf
|
62
|
-
tf
|
68
|
+
# use an ivar to avoid GC
|
69
|
+
@tf = Tempfile.new("childprocess-temp")
|
70
|
+
@tf << code
|
71
|
+
@tf.close
|
63
72
|
|
64
73
|
puts code if $DEBUG
|
65
74
|
|
66
|
-
tf.path
|
75
|
+
@tf.path
|
67
76
|
end
|
68
77
|
|
69
78
|
def within(seconds, &blk)
|
data/spec/unix_spec.rb
CHANGED
@@ -1,7 +1,10 @@
|
|
1
1
|
require File.expand_path('../spec_helper', __FILE__)
|
2
|
+
require "pid_behavior"
|
2
3
|
|
3
4
|
if ChildProcess.unix?
|
4
5
|
describe ChildProcess::Unix::Process do
|
6
|
+
it_behaves_like "a platform that provides the child's pid"
|
7
|
+
|
5
8
|
it "handles ECHILD race condition where process dies between timeout and KILL" do
|
6
9
|
process = sleeping_ruby
|
7
10
|
|
@@ -46,4 +49,4 @@ if ChildProcess.unix?
|
|
46
49
|
end
|
47
50
|
end
|
48
51
|
|
49
|
-
end
|
52
|
+
end
|
data/spec/windows_spec.rb
CHANGED
@@ -1,9 +1,12 @@
|
|
1
1
|
require File.expand_path('../spec_helper', __FILE__)
|
2
|
+
require "pid_behavior"
|
2
3
|
|
3
4
|
if ChildProcess.windows?
|
4
5
|
describe ChildProcess::Windows::IO do
|
5
6
|
let(:io) { ChildProcess::Windows::IO.new }
|
6
7
|
|
8
|
+
it_behaves_like "a platform that provides the child's pid"
|
9
|
+
|
7
10
|
it "raises an ArgumentError if given IO does not respond to :fileno" do
|
8
11
|
lambda { io.stdout = nil }.should raise_error(ArgumentError, /must have :fileno or :to_io/)
|
9
12
|
end
|
@@ -15,4 +18,4 @@ if ChildProcess.windows?
|
|
15
18
|
lambda { io.stdout = fake_io }.should raise_error(ArgumentError, /must have :fileno or :to_io/)
|
16
19
|
end
|
17
20
|
end
|
18
|
-
end
|
21
|
+
end
|
metadata
CHANGED
@@ -1,12 +1,8 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: childprocess
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
prerelease:
|
5
|
-
|
6
|
-
- 0
|
7
|
-
- 1
|
8
|
-
- 6
|
9
|
-
version: 0.1.6
|
4
|
+
prerelease:
|
5
|
+
version: 0.1.7
|
10
6
|
platform: ruby
|
11
7
|
authors:
|
12
8
|
- Jari Bakken
|
@@ -14,7 +10,7 @@ autorequire:
|
|
14
10
|
bindir: bin
|
15
11
|
cert_chain: []
|
16
12
|
|
17
|
-
date:
|
13
|
+
date: 2011-02-12 00:00:00 +01:00
|
18
14
|
default_executable:
|
19
15
|
dependencies:
|
20
16
|
- !ruby/object:Gem::Dependency
|
@@ -25,10 +21,6 @@ dependencies:
|
|
25
21
|
requirements:
|
26
22
|
- - ">="
|
27
23
|
- !ruby/object:Gem::Version
|
28
|
-
segments:
|
29
|
-
- 2
|
30
|
-
- 0
|
31
|
-
- 0
|
32
24
|
version: 2.0.0
|
33
25
|
type: :development
|
34
26
|
version_requirements: *id001
|
@@ -40,8 +32,6 @@ dependencies:
|
|
40
32
|
requirements:
|
41
33
|
- - ">="
|
42
34
|
- !ruby/object:Gem::Version
|
43
|
-
segments:
|
44
|
-
- 0
|
45
35
|
version: "0"
|
46
36
|
type: :development
|
47
37
|
version_requirements: *id002
|
@@ -53,10 +43,6 @@ dependencies:
|
|
53
43
|
requirements:
|
54
44
|
- - ~>
|
55
45
|
- !ruby/object:Gem::Version
|
56
|
-
segments:
|
57
|
-
- 0
|
58
|
-
- 6
|
59
|
-
- 3
|
60
46
|
version: 0.6.3
|
61
47
|
type: :runtime
|
62
48
|
version_requirements: *id003
|
@@ -101,6 +87,7 @@ files:
|
|
101
87
|
- spec/abstract_io_spec.rb
|
102
88
|
- spec/childprocess_spec.rb
|
103
89
|
- spec/jruby_spec.rb
|
90
|
+
- spec/pid_behavior.rb
|
104
91
|
- spec/spec_helper.rb
|
105
92
|
- spec/unix_spec.rb
|
106
93
|
- spec/windows_spec.rb
|
@@ -118,21 +105,17 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
118
105
|
requirements:
|
119
106
|
- - ">="
|
120
107
|
- !ruby/object:Gem::Version
|
121
|
-
segments:
|
122
|
-
- 0
|
123
108
|
version: "0"
|
124
109
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
125
110
|
none: false
|
126
111
|
requirements:
|
127
112
|
- - ">="
|
128
113
|
- !ruby/object:Gem::Version
|
129
|
-
segments:
|
130
|
-
- 0
|
131
114
|
version: "0"
|
132
115
|
requirements: []
|
133
116
|
|
134
117
|
rubyforge_project:
|
135
|
-
rubygems_version: 1.
|
118
|
+
rubygems_version: 1.5.0
|
136
119
|
signing_key:
|
137
120
|
specification_version: 3
|
138
121
|
summary: Cross-platform ruby library for managing child processes.
|
@@ -140,6 +123,7 @@ test_files:
|
|
140
123
|
- spec/abstract_io_spec.rb
|
141
124
|
- spec/childprocess_spec.rb
|
142
125
|
- spec/jruby_spec.rb
|
126
|
+
- spec/pid_behavior.rb
|
143
127
|
- spec/spec_helper.rb
|
144
128
|
- spec/unix_spec.rb
|
145
129
|
- spec/windows_spec.rb
|