multi_process 0.1.0 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/multi_process/group.rb +31 -4
- data/lib/multi_process/logger.rb +1 -1
- data/lib/multi_process/process.rb +5 -6
- data/lib/multi_process/version.rb +1 -1
- data/spec/files/test.rb +1 -1
- data/spec/multi_process_spec.rb +24 -8
- metadata +1 -1
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 12b6e61ecec6390d6c06f1ddbdc1a9288f65c0c1
|
4
|
+
data.tar.gz: b09e0b1587f578428daa05bb4dacb1fe11324dc9
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 8e3e41b5665d57220412d203735786c7ae506386824cd3c6b00830692414c81e7dfdf4d697321ebffccb7d420e661018e45efe19e94712ceaad91bd38a8d7ef7
|
7
|
+
data.tar.gz: c57700b68cc35c3a5f63268d70ed10a89d04069e7e87f08418c8513e30c9571716b1a53699713cd83ee61846030997e2547251ab05b93b5ebf6814641fbe561c
|
data/lib/multi_process/group.rb
CHANGED
@@ -13,6 +13,9 @@ module MultiProcess
|
|
13
13
|
#
|
14
14
|
attr_accessor :receiver
|
15
15
|
|
16
|
+
# Partition size.
|
17
|
+
attr_reader :partition
|
18
|
+
|
16
19
|
# Create new process group.
|
17
20
|
#
|
18
21
|
# @param opts [ Hash ] Options
|
@@ -22,6 +25,8 @@ module MultiProcess
|
|
22
25
|
def initialize(opts = {})
|
23
26
|
@processes = []
|
24
27
|
@receiver = opts[:receiver] ? opts[:receiver] : MultiProcess::Logger.global
|
28
|
+
@partition = opts[:partition] ? opts[:partition].to_i : 0
|
29
|
+
@mutex = Mutex.new
|
25
30
|
end
|
26
31
|
|
27
32
|
# Add new process or list of processes.
|
@@ -33,7 +38,7 @@ module MultiProcess
|
|
33
38
|
def <<(process)
|
34
39
|
Array(process).flatten.each do |process|
|
35
40
|
processes << process
|
36
|
-
|
41
|
+
process.receiver = receiver
|
37
42
|
|
38
43
|
if started?
|
39
44
|
start process
|
@@ -89,14 +94,27 @@ module MultiProcess
|
|
89
94
|
|
90
95
|
# Start all process and wait for them to terminate.
|
91
96
|
#
|
92
|
-
# Given options will be passed to {#wait}.
|
97
|
+
# Given options will be passed to {#start} and {#wait}.
|
98
|
+
# {#start} will only be called if partition is zero.
|
93
99
|
#
|
94
100
|
# If timeout is given process will be terminated using {#stop}
|
95
101
|
# when timeout error is raised.
|
96
102
|
#
|
97
103
|
def run(opts = {})
|
98
|
-
|
99
|
-
|
104
|
+
if partition > 0
|
105
|
+
threads = Array.new
|
106
|
+
partition.times do
|
107
|
+
threads << Thread.new do
|
108
|
+
while (process = next_process)
|
109
|
+
process.run
|
110
|
+
end
|
111
|
+
end
|
112
|
+
end
|
113
|
+
threads.each &:join
|
114
|
+
else
|
115
|
+
start opts
|
116
|
+
wait opts
|
117
|
+
end
|
100
118
|
ensure
|
101
119
|
stop
|
102
120
|
end
|
@@ -132,5 +150,14 @@ module MultiProcess
|
|
132
150
|
processes.each{|p| p.available! }
|
133
151
|
end
|
134
152
|
end
|
153
|
+
|
154
|
+
private
|
155
|
+
def next_process
|
156
|
+
@mutex.synchronize do
|
157
|
+
@index ||= 0
|
158
|
+
@index += 1
|
159
|
+
processes[@index - 1]
|
160
|
+
end
|
161
|
+
end
|
135
162
|
end
|
136
163
|
end
|
data/lib/multi_process/logger.rb
CHANGED
@@ -187,13 +187,12 @@ module MultiProcess
|
|
187
187
|
#
|
188
188
|
def start_childprocess
|
189
189
|
env.each{|k, v| childprocess.environment[k.to_s] = v.to_s }
|
190
|
+
childprocess.cwd = dir
|
190
191
|
|
191
|
-
|
192
|
-
|
193
|
-
|
194
|
-
|
195
|
-
childprocess.start
|
196
|
-
end
|
192
|
+
if clean_env?
|
193
|
+
Bundler.with_clean_env { childprocess.start }
|
194
|
+
else
|
195
|
+
childprocess.start
|
197
196
|
end
|
198
197
|
end
|
199
198
|
end
|
data/spec/files/test.rb
CHANGED
data/spec/multi_process_spec.rb
CHANGED
@@ -6,26 +6,26 @@ describe MultiProcess do
|
|
6
6
|
reader, writer = IO.pipe
|
7
7
|
|
8
8
|
logger = MultiProcess::Logger.new writer
|
9
|
-
group = MultiProcess::Group.new
|
9
|
+
group = MultiProcess::Group.new receiver: logger
|
10
10
|
group << MultiProcess::Process.new(%w(ruby spec/files/test.rb A), title: 'rubyA')
|
11
11
|
group << MultiProcess::Process.new(%w(ruby spec/files/test.rb B), title: 'rubyB')
|
12
12
|
group << MultiProcess::Process.new(%w(ruby spec/files/test.rb C), title: 'rubyC')
|
13
13
|
group.run
|
14
14
|
|
15
15
|
expect(reader.read_nonblock(4096).split("\n")).to match_array <<-EOF.gsub(/^\s+/, ' ').split("\n")
|
16
|
-
rubyB
|
17
|
-
rubyA
|
18
|
-
rubyA
|
19
|
-
rubyC
|
20
|
-
rubyC
|
21
|
-
rubyB
|
16
|
+
rubyB | Output from B
|
17
|
+
rubyA | Output from A
|
18
|
+
rubyA | Output from A
|
19
|
+
rubyC | Output from C
|
20
|
+
rubyC | Output from C
|
21
|
+
rubyB | Output from B
|
22
22
|
EOF
|
23
23
|
end
|
24
24
|
|
25
25
|
it 'should run processes' do
|
26
26
|
start = Time.now
|
27
27
|
|
28
|
-
group = MultiProcess::Group.new
|
28
|
+
group = MultiProcess::Group.new receiver: MultiProcess::NilReceiver.new
|
29
29
|
group << MultiProcess::Process.new(%w(ruby spec/files/sleep.rb 5000), title: 'rubyA')
|
30
30
|
group << MultiProcess::Process.new(%w(ruby spec/files/sleep.rb 5000), title: 'rubyB')
|
31
31
|
group << MultiProcess::Process.new(%w(ruby spec/files/sleep.rb 5000), title: 'rubyC')
|
@@ -38,4 +38,20 @@ describe MultiProcess do
|
|
38
38
|
end
|
39
39
|
expect(Time.now - start).to be < 2
|
40
40
|
end
|
41
|
+
|
42
|
+
it 'should partition processes' do
|
43
|
+
group = MultiProcess::Group.new partition: 4, receiver: MultiProcess::NilReceiver.new
|
44
|
+
group << MultiProcess::Process.new(%w(ruby sleep.rb 1), dir: 'spec/files', title: 'rubyA')
|
45
|
+
group << MultiProcess::Process.new(%w(ruby sleep.rb 1), dir: 'spec/files', title: 'rubyB')
|
46
|
+
group << MultiProcess::Process.new(%w(ruby sleep.rb 1), dir: 'spec/files', title: 'rubyC')
|
47
|
+
group << MultiProcess::Process.new(%w(ruby sleep.rb 1), dir: 'spec/files', title: 'rubyD')
|
48
|
+
group << MultiProcess::Process.new(%w(ruby sleep.rb 1), dir: 'spec/files', title: 'rubyE')
|
49
|
+
group << MultiProcess::Process.new(%w(ruby sleep.rb 1), dir: 'spec/files', title: 'rubyF')
|
50
|
+
group << MultiProcess::Process.new(%w(ruby sleep.rb 1), dir: 'spec/files', title: 'rubyG')
|
51
|
+
group << MultiProcess::Process.new(%w(ruby sleep.rb 1), dir: 'spec/files', title: 'rubyH')
|
52
|
+
|
53
|
+
start = Time.now
|
54
|
+
group.run
|
55
|
+
expect(Time.now - start).to be_within(0.3).of(2)
|
56
|
+
end
|
41
57
|
end
|