ruby_process 0.0.5 → 0.0.7

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.
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.0.5
1
+ 0.0.7
@@ -74,11 +74,16 @@ class Ruby_process
74
74
  if args and args[:exec]
75
75
  cmd = "#{args[:exec]}"
76
76
  else
77
- cmd = "ruby"
77
+ if !ENV["rvm_ruby_string"].to_s.empty?
78
+ cmd = "#{ENV["rvm_ruby_string"]}"
79
+ else
80
+ cmd = "ruby"
81
+ end
78
82
  end
79
83
 
80
84
  cmd << " \"#{File.realpath(File.dirname(__FILE__))}/../scripts/ruby_process_script.rb\" --pid=#{@my_pid}"
81
85
  cmd << " --debug" if @args[:debug]
86
+ cmd << " \"--title=#{@args[:title]}\"" if !@args[:title].to_s.strip.empty?
82
87
 
83
88
  #Start process and set IO variables.
84
89
  require "open3"
@@ -117,7 +122,7 @@ class Ruby_process
117
122
  self.destroy
118
123
  end
119
124
 
120
- return nil
125
+ return self
121
126
  else
122
127
  return self
123
128
  end
@@ -164,7 +169,7 @@ class Ruby_process
164
169
 
165
170
  #Sends a command to the other process. This should not be called manually, but is used by various other parts of the framework.
166
171
  def send(obj, &block)
167
- raise "Ruby-process is dead." if !alive?
172
+ alive_check!
168
173
 
169
174
  #Parse block.
170
175
  if block
@@ -196,11 +201,22 @@ class Ruby_process
196
201
  :type => :send,
197
202
  :obj => obj
198
203
  ))
204
+ @answers[id] = Queue.new
199
205
  @io_out.puts(line)
200
- sleep 0.001
206
+
201
207
  return answer_read(id)
202
208
  end
203
209
 
210
+ #Returns true if the child process is still running. Otherwise false.
211
+ def alive?
212
+ begin
213
+ self.alive_check!
214
+ return true
215
+ rescue
216
+ return false
217
+ end
218
+ end
219
+
204
220
  private
205
221
 
206
222
  def debug(str_full)
@@ -215,15 +231,14 @@ class Ruby_process
215
231
  end
216
232
  end
217
233
 
218
- #Returns true if the child process is still running. Otherwise false.
219
- def alive?
220
- return false if !@io_out or !@io_in or @io_in.closed?
221
- return true
222
- end
223
-
224
234
  #Raises an error if the subprocess is no longer alive.
225
235
  def alive_check!
226
- raise "Process is dead." unless alive?
236
+ raise "No 'io_out'." if !@io_out
237
+ raise "No 'io_in'." if !@io_in
238
+ raise "'io_in' was closed." if @io_in.closed?
239
+ raise "No listen thread." if !@thr_listen
240
+ raise "Listen thread wasnt alive?" if !@thr_listen.alive?
241
+
227
242
  return nil
228
243
  end
229
244
 
@@ -267,39 +282,29 @@ class Ruby_process
267
282
  #Waits for an answer to appear in the answers-hash. Then deletes it from hash and returns it.
268
283
  def answer_read(id)
269
284
  debug "Waiting for answer #{id}\n" if @debug
285
+ answer = @answers[id].pop
270
286
 
271
- loop do
272
- if @answers.key?(id)
273
- debug "Returning answer #{id}\n" if @debug
274
- answer = @answers[id]
275
- @answers.delete(id)
276
-
277
- if answer.is_a?(Hash) and answer[:type] == :error and answer.key?(:class) and answer.key?(:msg) and answer.key?(:bt)
278
- begin
279
- raise "#{answer[:class]}: #{answer[:msg]}"
280
- rescue => e
281
- bt = []
282
- answer[:bt].each do |btline|
283
- bt << "(#{@pid}): #{btline}"
284
- end
285
-
286
- bt += e.backtrace
287
- e.set_backtrace(bt)
288
- raise e
289
- end
290
- elsif answer.is_a?(Hash) and answer[:type] == :proxy_obj and answer.key?(:id)
291
- return proxyobj_get(answer[:id], answer[:pid])
287
+ debug "Returning answer #{id}\n" if @debug
288
+ @answers.delete(id)
289
+
290
+ if answer.is_a?(Hash) and answer[:type] == :error and answer.key?(:class) and answer.key?(:msg) and answer.key?(:bt)
291
+ begin
292
+ raise "#{answer[:class]}: #{answer[:msg]}"
293
+ rescue => e
294
+ bt = []
295
+ answer[:bt].each do |btline|
296
+ bt << "(#{@pid}): #{btline}"
292
297
  end
293
298
 
294
- return answer
299
+ bt += e.backtrace
300
+ e.set_backtrace(bt)
301
+ raise e
295
302
  end
296
-
297
- debug "No answer by ID #{id} - sleeping...\n" if @debug
298
- sleep 0.01
299
- alive_check!
300
- raise @listen_err if @listen_err
301
- raise "Not listening." if !@thr_listen or !@thr_listen.alive?
303
+ elsif answer.is_a?(Hash) and answer[:type] == :proxy_obj and answer.key?(:id)
304
+ return proxyobj_get(answer[:id], answer[:pid])
302
305
  end
306
+
307
+ return answer
303
308
  end
304
309
 
305
310
  #Starts the listen-thread that listens for, and executes, commands.
@@ -336,9 +341,9 @@ class Ruby_process
336
341
  data = Base64.strict_encode64(Marshal.dump(:type => :answer, :id => obj[:id], :answer => res))
337
342
  @io_out.puts(data)
338
343
  end
339
- elsif obj[:type] == :answer
340
- debug "Answer #{obj[:id]} saved.\n" if @debug
341
- @answers[obj[:id]] = obj[:answer]
344
+ elsif obj[:type] == :answer and id = obj[:id].to_i
345
+ debug "Answer #{id} saved.\n" if @debug
346
+ @answers[id] << obj[:answer]
342
347
  else
343
348
  raise "Unknown object: '#{obj}'."
344
349
  end
@@ -363,39 +368,4 @@ class Ruby_process
363
368
  end
364
369
  end
365
370
  end
366
- end
367
-
368
- #This class handels the calling of methods on objects in the other process seamlessly.
369
- class Ruby_process::Proxyobj
370
- #Hash that contains various information about the proxyobj.
371
- attr_reader :args
372
-
373
- #Constructor. This should not be called manually but through a running 'Ruby_process'.
374
- #===Examples
375
- # proxy_obj = rp.new(:String, "Kasper") #=> <Ruby_process::Proxyobj>
376
- # proxy_obj = rp.static(:File, :open, "/tmp/somefile") #=> <Ruby_process::Proxyobj>
377
- def initialize(args)
378
- @args = args
379
- end
380
-
381
- #Returns the object as the real object transfered by using the marshal-lib.
382
- #===Examples
383
- # str = rp.new(:String, "Kasper") #=> <Ruby_process::Proxyobj>
384
- # str.__rp_marshal #=> "Kasper"
385
- def __rp_marshal
386
- return Marshal.load(@args[:rp].send(:cmd => :obj_marshal, :id => @args[:id]))
387
- end
388
-
389
- #Proxies all calls to the process-object.
390
- #===Examples
391
- # str = rp.new(:String, "Kasper") #=> <Ruby_process::Proxyobj::1>
392
- # length_int = str.length #=> <Ruby_process::Proxyobj::2>
393
- # length_int.__rp_marshal #=> 6
394
- def method_missing(method, *args, &block)
395
- debug "Method-missing-args-before: #{args} (#{@my_pid})\n" if @debug
396
- real_args = @args[:rp].parse_args(args)
397
- debug "Method-missing-args-after: #{real_args}\n" if @debug
398
-
399
- return @args[:rp].send(:cmd => :obj_method, :id => @args[:id], :method => method, :args => real_args, &block)
400
- end
401
371
  end
@@ -27,8 +27,15 @@ class Ruby_process::Cproxy
27
27
  @@lock.synchronize do
28
28
  @@instances += 1
29
29
 
30
+ #Check if the sub-process is alive.
31
+ if @@subproc and !@@subproc.alive?
32
+ @@subproc.destroy
33
+ @@subproc = nil
34
+ end
35
+
36
+ #Start a new subprocess if none is defined and active.
30
37
  if !@@subproc
31
- @@subproc = Ruby_process.new
38
+ @@subproc = Ruby_process.new(:title => "cproxy", :debug => false)
32
39
  @@subproc.spawn_process
33
40
  end
34
41
  end
@@ -0,0 +1,50 @@
1
+ #This class handels the calling of methods on objects in the other process seamlessly.
2
+ class Ruby_process::Proxyobj
3
+ #Hash that contains various information about the proxyobj.
4
+ attr_reader :args
5
+
6
+ #Constructor. This should not be called manually but through a running 'Ruby_process'.
7
+ #===Examples
8
+ # proxy_obj = rp.new(:String, "Kasper") #=> <Ruby_process::Proxyobj>
9
+ # proxy_obj = rp.static(:File, :open, "/tmp/somefile") #=> <Ruby_process::Proxyobj>
10
+ def initialize(args)
11
+ @args = args
12
+ end
13
+
14
+ #Returns the object as the real object transfered by using the marshal-lib.
15
+ #===Examples
16
+ # str = rp.new(:String, "Kasper") #=> <Ruby_process::Proxyobj>
17
+ # str.__rp_marshal #=> "Kasper"
18
+ def __rp_marshal
19
+ return Marshal.load(@args[:rp].send(:cmd => :obj_marshal, :id => @args[:id]))
20
+ end
21
+
22
+ #Overwrite certain convert methods.
23
+ RUBY_METHODS = [:to_i, :to_s, :to_str, :to_f]
24
+ RUBY_METHODS.each do |method_name|
25
+ define_method(method_name) do |*args, &blk|
26
+ return @args[:rp].send(:cmd => :obj_method, :id => @args[:id], :method => method_name, :args => args, &blk).__rp_marshal
27
+ end
28
+ end
29
+
30
+ #Overwrite certain methods.
31
+ PROXY_METHODS = [:send]
32
+ PROXY_METHODS.each do |method_name|
33
+ define_method(method_name) do |*args, &blk|
34
+ self.method_missing(method_name, *args, &blk)
35
+ end
36
+ end
37
+
38
+ #Proxies all calls to the process-object.
39
+ #===Examples
40
+ # str = rp.new(:String, "Kasper") #=> <Ruby_process::Proxyobj::1>
41
+ # length_int = str.length #=> <Ruby_process::Proxyobj::2>
42
+ # length_int.__rp_marshal #=> 6
43
+ def method_missing(method, *args, &block)
44
+ debug "Method-missing-args-before: #{args} (#{@my_pid})\n" if @debug
45
+ real_args = @args[:rp].parse_args(args)
46
+ debug "Method-missing-args-after: #{real_args}\n" if @debug
47
+
48
+ return @args[:rp].send(:cmd => :obj_method, :id => @args[:id], :method => method, :args => real_args, &block)
49
+ end
50
+ end
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{ruby_process}
8
- s.version = "0.0.5"
8
+ s.version = "0.0.7"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Kasper Johansen"]
12
- s.date = %q{2012-10-14}
12
+ s.date = %q{2012-10-16}
13
13
  s.description = %q{A framework for spawning and communicating with other Ruby-processes}
14
14
  s.email = %q{k@spernj.org}
15
15
  s.extra_rdoc_files = [
@@ -37,9 +37,11 @@ Gem::Specification.new do |s|
37
37
  "include/args_handeling.rb",
38
38
  "lib/ruby_process.rb",
39
39
  "lib/ruby_process_cproxy.rb",
40
+ "lib/ruby_process_proxyobj.rb",
40
41
  "ruby_process.gemspec",
41
42
  "scripts/ruby_process_script.rb",
42
43
  "spec/cproxy_spec.rb",
44
+ "spec/hard_load_spec.rb",
43
45
  "spec/ruby_process_spec.rb",
44
46
  "spec/spec_helper.rb"
45
47
  ]
@@ -13,8 +13,10 @@ pid = nil
13
13
  ARGV.each do |arg|
14
14
  if arg == "--debug"
15
15
  debug = true
16
- elsif match = arg.match(/--pid=(\d+)/)
16
+ elsif match = arg.match(/--pid=(\d+)$/)
17
17
  pid = match[1].to_i
18
+ elsif match = arg.match(/--title=(.+)$/)
19
+ #ignore - its for finding process via 'ps aux'.
18
20
  else
19
21
  raise "Unknown argument: '#{arg}'."
20
22
  end
@@ -0,0 +1,39 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe "RubyProcess" do
4
+ it "should be able to do basic stuff" do
5
+ Ruby_process::Cproxy.run do |data|
6
+ sp = data[:subproc]
7
+ sp.new(:String, "Wee")
8
+
9
+ ts = []
10
+
11
+ 1.upto(50) do |tcount|
12
+ ts << Thread.new do
13
+ 1.upto(250) do
14
+ str = sp.new(:String, "Kasper Johansen")
15
+
16
+ res1 = str.include?("Kasper")
17
+ str << " More"
18
+
19
+ res2 = str.include?("Johansen")
20
+ str << " Even more"
21
+
22
+ res3 = str.include?("Christina")
23
+ str << " Much more"
24
+
25
+ raise "Expected res1 to be true but it wasnt: '#{res1}'." if res1 != true
26
+ raise "Expected res2 to be true but it wasnt: '#{res2}'." if res2 != true
27
+ raise "Expected res3 to be false but it wasnt: '#{res3}'." if res3 != false
28
+
29
+ print "."
30
+ end
31
+ end
32
+ end
33
+
34
+ ts.each do |t|
35
+ t.join
36
+ end
37
+ end
38
+ end
39
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: ruby_process
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.5
4
+ version: 0.0.7
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,12 +9,12 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2012-10-14 00:00:00.000000000 +02:00
12
+ date: 2012-10-16 00:00:00.000000000 +02:00
13
13
  default_executable:
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: wref
17
- requirement: &12566380 !ruby/object:Gem::Requirement
17
+ requirement: &19833520 !ruby/object:Gem::Requirement
18
18
  none: false
19
19
  requirements:
20
20
  - - ! '>='
@@ -22,10 +22,10 @@ dependencies:
22
22
  version: '0'
23
23
  type: :runtime
24
24
  prerelease: false
25
- version_requirements: *12566380
25
+ version_requirements: *19833520
26
26
  - !ruby/object:Gem::Dependency
27
27
  name: tsafe
28
- requirement: &12565660 !ruby/object:Gem::Requirement
28
+ requirement: &19832660 !ruby/object:Gem::Requirement
29
29
  none: false
30
30
  requirements:
31
31
  - - ! '>='
@@ -33,10 +33,10 @@ dependencies:
33
33
  version: '0'
34
34
  type: :runtime
35
35
  prerelease: false
36
- version_requirements: *12565660
36
+ version_requirements: *19832660
37
37
  - !ruby/object:Gem::Dependency
38
38
  name: rspec
39
- requirement: &12564900 !ruby/object:Gem::Requirement
39
+ requirement: &19831800 !ruby/object:Gem::Requirement
40
40
  none: false
41
41
  requirements:
42
42
  - - ~>
@@ -44,10 +44,10 @@ dependencies:
44
44
  version: 2.8.0
45
45
  type: :development
46
46
  prerelease: false
47
- version_requirements: *12564900
47
+ version_requirements: *19831800
48
48
  - !ruby/object:Gem::Dependency
49
49
  name: rdoc
50
- requirement: &12564260 !ruby/object:Gem::Requirement
50
+ requirement: &19830660 !ruby/object:Gem::Requirement
51
51
  none: false
52
52
  requirements:
53
53
  - - ~>
@@ -55,10 +55,10 @@ dependencies:
55
55
  version: '3.12'
56
56
  type: :development
57
57
  prerelease: false
58
- version_requirements: *12564260
58
+ version_requirements: *19830660
59
59
  - !ruby/object:Gem::Dependency
60
60
  name: bundler
61
- requirement: &12563400 !ruby/object:Gem::Requirement
61
+ requirement: &19828180 !ruby/object:Gem::Requirement
62
62
  none: false
63
63
  requirements:
64
64
  - - ! '>='
@@ -66,10 +66,10 @@ dependencies:
66
66
  version: 1.0.0
67
67
  type: :development
68
68
  prerelease: false
69
- version_requirements: *12563400
69
+ version_requirements: *19828180
70
70
  - !ruby/object:Gem::Dependency
71
71
  name: jeweler
72
- requirement: &12562600 !ruby/object:Gem::Requirement
72
+ requirement: &19827260 !ruby/object:Gem::Requirement
73
73
  none: false
74
74
  requirements:
75
75
  - - ~>
@@ -77,10 +77,10 @@ dependencies:
77
77
  version: 1.8.3
78
78
  type: :development
79
79
  prerelease: false
80
- version_requirements: *12562600
80
+ version_requirements: *19827260
81
81
  - !ruby/object:Gem::Dependency
82
82
  name: rcov
83
- requirement: &12561560 !ruby/object:Gem::Requirement
83
+ requirement: &19826400 !ruby/object:Gem::Requirement
84
84
  none: false
85
85
  requirements:
86
86
  - - ! '>='
@@ -88,7 +88,7 @@ dependencies:
88
88
  version: '0'
89
89
  type: :development
90
90
  prerelease: false
91
- version_requirements: *12561560
91
+ version_requirements: *19826400
92
92
  description: A framework for spawning and communicating with other Ruby-processes
93
93
  email: k@spernj.org
94
94
  executables: []
@@ -117,9 +117,11 @@ files:
117
117
  - include/args_handeling.rb
118
118
  - lib/ruby_process.rb
119
119
  - lib/ruby_process_cproxy.rb
120
+ - lib/ruby_process_proxyobj.rb
120
121
  - ruby_process.gemspec
121
122
  - scripts/ruby_process_script.rb
122
123
  - spec/cproxy_spec.rb
124
+ - spec/hard_load_spec.rb
123
125
  - spec/ruby_process_spec.rb
124
126
  - spec/spec_helper.rb
125
127
  has_rdoc: true
@@ -138,7 +140,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
138
140
  version: '0'
139
141
  segments:
140
142
  - 0
141
- hash: 4244816793884101144
143
+ hash: 1714435591026867569
142
144
  required_rubygems_version: !ruby/object:Gem::Requirement
143
145
  none: false
144
146
  requirements: