slave 1.2.2 → 1.3.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,158 +0,0 @@
1
- <?xml version="1.0" encoding="iso-8859-1"?>
2
- <!DOCTYPE html
3
- PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
4
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
5
-
6
- <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
7
- <head>
8
- <title>Class: Slave::ThreadSafeHash</title>
9
- <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
10
- <meta http-equiv="Content-Script-Type" content="text/javascript" />
11
- <link rel="stylesheet" href="../.././rdoc-style.css" type="text/css" media="screen" />
12
- <script type="text/javascript">
13
- // <![CDATA[
14
-
15
- function popupCode( url ) {
16
- window.open(url, "Code", "resizable=yes,scrollbars=yes,toolbar=no,status=no,height=150,width=400")
17
- }
18
-
19
- function toggleCode( id ) {
20
- if ( document.getElementById )
21
- elem = document.getElementById( id );
22
- else if ( document.all )
23
- elem = eval( "document.all." + id );
24
- else
25
- return false;
26
-
27
- elemStyle = elem.style;
28
-
29
- if ( elemStyle.display != "block" ) {
30
- elemStyle.display = "block"
31
- } else {
32
- elemStyle.display = "none"
33
- }
34
-
35
- return true;
36
- }
37
-
38
- // Make codeblocks hidden by default
39
- document.writeln( "<style type=\"text/css\">div.method-source-code { display: none }</style>" )
40
-
41
- // ]]>
42
- </script>
43
-
44
- </head>
45
- <body>
46
-
47
-
48
-
49
- <div id="classHeader">
50
- <table class="header-table">
51
- <tr class="top-aligned-row">
52
- <td><strong>Class</strong></td>
53
- <td class="class-name-in-header">Slave::ThreadSafeHash</td>
54
- </tr>
55
- <tr class="top-aligned-row">
56
- <td><strong>In:</strong></td>
57
- <td>
58
- <a href="../../files/lib/slave_rb.html">
59
- lib/slave.rb
60
- </a>
61
- <br />
62
- </td>
63
- </tr>
64
-
65
- <tr class="top-aligned-row">
66
- <td><strong>Parent:</strong></td>
67
- <td>
68
- Hash
69
- </td>
70
- </tr>
71
- </table>
72
- </div>
73
- <!-- banner header -->
74
-
75
- <div id="bodyContent">
76
-
77
-
78
-
79
- <div id="contextContent">
80
- <div id="diagram">
81
- <map id="map" name="map">
82
- <area shape="rect" coords="27,50,99,98" href="../Slave.html" alt="Slave" />
83
- </map>
84
- <img src="../../dot/f_1.jpg" usemap="#map" border="0" alt="dot/f_1.jpg">
85
- </div>
86
-
87
- <div id="description">
88
- <p>
89
- a simple thread safe hash used to map object_id to a set of file
90
- descriptors in the <a href="LifeLine.html">LifeLine</a> class. see
91
- LifeLine::FDS
92
- </p>
93
-
94
- </div>
95
-
96
-
97
- </div>
98
-
99
- <div id="method-list">
100
- <h3 class="section-bar">Methods</h3>
101
-
102
- <div class="name-list">
103
- <a href="#M000030">new</a>&nbsp;&nbsp;
104
- </div>
105
- </div>
106
-
107
- </div>
108
-
109
-
110
- <!-- if includes -->
111
-
112
- <div id="section">
113
-
114
-
115
-
116
-
117
-
118
-
119
-
120
-
121
- <!-- if method_list -->
122
- <div id="methods">
123
- <h3 class="section-bar">Public Class methods</h3>
124
-
125
- <div id="method-M000030" class="method-detail">
126
- <a name="M000030"></a>
127
-
128
- <div class="method-heading">
129
- <a href="#M000030" class="method-signature">
130
- <span class="method-name">new</span><span class="method-args">(*a, &amp;b)</span>
131
- </a>
132
- </div>
133
-
134
- <div class="method-description">
135
- <p><a class="source-toggle" href="#"
136
- onclick="toggleCode('M000030-source');return false;">[Source]</a></p>
137
- <div class="method-source-code" id="M000030-source">
138
- <pre>
139
- <span class="ruby-comment cmt"># File lib/slave.rb, line 156</span>
140
- 156: <span class="ruby-keyword kw">def</span> <span class="ruby-keyword kw">self</span>.<span class="ruby-identifier">new</span>(<span class="ruby-operator">*</span><span class="ruby-identifier">a</span>, <span class="ruby-operator">&amp;</span><span class="ruby-identifier">b</span>) <span class="ruby-constant">ThreadSafe</span>.<span class="ruby-identifier">new</span>(<span class="ruby-keyword kw">super</span>) <span class="ruby-keyword kw">end</span>
141
- </pre>
142
- </div>
143
- </div>
144
- </div>
145
-
146
-
147
- </div>
148
-
149
-
150
- </div>
151
-
152
-
153
- <div id="validator-badges">
154
- <p><small><a href="http://validator.w3.org/check/referer">[Validate]</a></small></p>
155
- </div>
156
-
157
- </body>
158
- </html>
@@ -1,117 +0,0 @@
1
- <?xml version="1.0" encoding="iso-8859-1"?>
2
- <!DOCTYPE html
3
- PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
4
- "DTD/xhtml1-transitional.dtd">
5
-
6
- <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
7
- <head>
8
- <title>Class: o</title>
9
- <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
10
- <meta http-equiv="Content-Script-Type" content="text/javascript" />
11
- <link rel="stylesheet" href=".././rdoc-style.css" type="text/css" media="screen" />
12
- <script type="text/javascript">
13
- // <![CDATA[
14
-
15
- function popupCode( url ) {
16
- window.open(url, "Code", "resizable=yes,scrollbars=yes,toolbar=no,status=no,height=150,width=400")
17
- }
18
-
19
- function toggleCode( id ) {
20
- if ( document.getElementById )
21
- elem = document.getElementById( id );
22
- else if ( document.all )
23
- elem = eval( "document.all." + id );
24
- else
25
- return false;
26
-
27
- elemStyle = elem.style;
28
-
29
- if ( elemStyle.display != "block" ) {
30
- elemStyle.display = "block"
31
- } else {
32
- elemStyle.display = "none"
33
- }
34
-
35
- return true;
36
- }
37
-
38
- // Make codeblocks hidden by default
39
- document.writeln( "<style type=\"text/css\">div.method-source-code { display: none }</style>" )
40
-
41
- // ]]>
42
- </script>
43
-
44
- </head>
45
- <body>
46
-
47
-
48
-
49
- <div id="classHeader">
50
- <h1>o <sup class="type-note">(Class)</sup></h1>
51
- <table class="header-table">
52
- <tr class="top-aligned-row">
53
- <td><strong>In:</strong></td>
54
- <td>
55
- <a href="../files/lib/slave_rb.html">
56
- lib/slave.rb
57
- </a>
58
- <br />
59
- </td>
60
- </tr>
61
-
62
- </table>
63
- </div>
64
- <!-- banner header -->
65
-
66
- <div id="bodyContent">
67
-
68
-
69
- <div id="contextContent">
70
- <div id="diagram">
71
- <map name="map">
72
- <area shape="RECT" coords="123,98,195,50" href="o.html" alt="o">
73
- <area shape="RECT" coords="27,98,99,50" href="Slave.html" alt="Slave">
74
- </map>
75
- <img src="../dot/f_1.jpg" usemap="#map" border=0 alt="TopLevel">
76
- </div>
77
-
78
-
79
-
80
-
81
-
82
-
83
-
84
- <div id="attribute-list">
85
- <h2 class="section-bar">Attributes</h2>
86
-
87
- <div class="name-list">
88
- <table>
89
- <tr class="top-aligned-row context-row">
90
- <td class="context-item-name">__slave_object_failure__</td>
91
- <td class="context-item-value">&nbsp;[RW]&nbsp;</td>
92
- <td class="context-item-desc"></td>
93
- </tr>
94
- </table>
95
- </div>
96
- </div>
97
-
98
-
99
- </div>
100
-
101
-
102
-
103
- <!-- if includes -->
104
-
105
-
106
- <!-- if method_list -->
107
-
108
-
109
- </div>
110
-
111
-
112
- <div id="validator-badges">
113
- <p><small><a href="http://validator.w3.org/check/referer">[Validate]</a></small></p>
114
- </div>
115
-
116
- </body>
117
- </html>
@@ -1 +0,0 @@
1
- Fri, 27 Apr 2007 16:38:57 -0600
@@ -1,14 +0,0 @@
1
- digraph TopLevel {
2
- compound = true
3
- bgcolor = lightcyan1
4
- fontname = Arial
5
- fontsize = 8
6
- label = "TopLevel"
7
- node [
8
- fontname = Arial,
9
- fontsize = 8,
10
- color = black
11
- ]
12
-
13
- }
14
-
Binary file
@@ -1,29 +0,0 @@
1
- digraph TopLevel {
2
- compound = true
3
- bgcolor = lightcyan1
4
- fontname = Arial
5
- fontsize = 8
6
- label = "TopLevel"
7
- node [
8
- fontname = Arial,
9
- fontsize = 8,
10
- color = black
11
- ]
12
-
13
- subgraph cluster_1 {
14
- fontname = Arial
15
- color = red
16
- label = "lib/slave.rb"
17
- Slave [
18
- fontcolor = black,
19
- URL = "classes/Slave.html",
20
- shape = ellipse,
21
- color = palegoldenrod,
22
- style = filled,
23
- label = "Slave"
24
- ]
25
-
26
- }
27
-
28
- }
29
-
Binary file
@@ -1,411 +0,0 @@
1
- <?xml version="1.0" encoding="iso-8859-1"?>
2
- <!DOCTYPE html
3
- PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
4
- "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
5
-
6
- <html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
7
- <head>
8
- <title>File: README</title>
9
- <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
10
- <meta http-equiv="Content-Script-Type" content="text/javascript" />
11
- <link rel="stylesheet" href=".././rdoc-style.css" type="text/css" media="screen" />
12
- <script type="text/javascript">
13
- // <![CDATA[
14
-
15
- function popupCode( url ) {
16
- window.open(url, "Code", "resizable=yes,scrollbars=yes,toolbar=no,status=no,height=150,width=400")
17
- }
18
-
19
- function toggleCode( id ) {
20
- if ( document.getElementById )
21
- elem = document.getElementById( id );
22
- else if ( document.all )
23
- elem = eval( "document.all." + id );
24
- else
25
- return false;
26
-
27
- elemStyle = elem.style;
28
-
29
- if ( elemStyle.display != "block" ) {
30
- elemStyle.display = "block"
31
- } else {
32
- elemStyle.display = "none"
33
- }
34
-
35
- return true;
36
- }
37
-
38
- // Make codeblocks hidden by default
39
- document.writeln( "<style type=\"text/css\">div.method-source-code { display: none }</style>" )
40
-
41
- // ]]>
42
- </script>
43
-
44
- </head>
45
- <body>
46
-
47
-
48
-
49
- <div id="fileHeader">
50
- <h1>README</h1>
51
- <table class="header-table">
52
- <tr class="top-aligned-row">
53
- <td><strong>Path:</strong></td>
54
- <td>README
55
- </td>
56
- </tr>
57
- <tr class="top-aligned-row">
58
- <td><strong>Last Update:</strong></td>
59
- <td>Fri, Apr 27 2007 16:38:30 -0600</td>
60
- </tr>
61
- </table>
62
- </div>
63
- <!-- banner header -->
64
-
65
- <div id="bodyContent">
66
-
67
-
68
-
69
- <div id="contextContent">
70
- <div id="diagram">
71
- <map id="map" name="map">
72
- </map>
73
- <img src="../dot/f_0.jpg" usemap="#map" border="0" alt="dot/f_0.jpg">
74
- </div>
75
-
76
- <div id="description">
77
- <p>
78
- SYNOPSIS
79
- </p>
80
- <pre>
81
- the Slave class forks a process and starts a drb server in the child using
82
- any object as the server. the process is detached so it is not required
83
- (nor possible) to wait on the child pid. a Heartbeat is set up between the
84
- parent and child processes so that the child will exit of the parent exits
85
- for any reason - preventing orphaned slaves from running indefinitely. the
86
- purpose of Slaves is to be able to easily set up a collection of objects
87
- communicating via drb protocols instead of having to use IPC.
88
-
89
- typical usage:
90
-
91
- slave = Slave::new{ AnyObject.new }
92
-
93
- slave.object #=&gt; handle on drb object
94
- slave.uri #=&gt; uri of the drb object
95
- slave.socket #=&gt; unix domain socket path for drb object
96
- slave.psname #=&gt; title shown in ps/top
97
-
98
- object = slave.object
99
-
100
- value = object.any_method #=&gt; use the object normally
101
-
102
- slaves may be configured via the environment, the Slave class, or via the
103
- ctor for object itself. attributes which may be configured include
104
-
105
- * object : specify the slave object. otherwise block value is used.
106
- * socket_creation_attempts : specify how many attempts to create a unix domain socket will be made
107
- * debug : turn on some logging to STDERR
108
- * psname : specify the name that will appear in 'top' ($0)
109
- * at_exit : specify a lambda to be called in the *parent* when the child dies
110
- * dumped : specify that the slave object should *not* be DRbUndumped (default is DRbUndumped)
111
- * threadsafe : wrap the slave object with ThreadSafe to implement gross thread safety
112
- </pre>
113
- <p>
114
- URIS
115
- </p>
116
- <pre>
117
- http://rubyforge.org/projects/codeforpeople/
118
- http://codeforpeople.com/lib/ruby/slave
119
- </pre>
120
- <p>
121
- HISTORY
122
- </p>
123
- <pre>
124
- 1.2.1:
125
- - jruby/ThreadSafe patches from skaar and ez. using slave.rb with jruby,
126
- how is that!?
127
-
128
- 1.2.0:
129
- - cleaned up a bunch of warnings. thanks eric kolve &lt;ekolve@gmail.com&gt;
130
- for reporting them.
131
-
132
- 1.1.0:
133
- - replaced HeartBeat class with LifeLine.
134
-
135
- - __HUGE__ cleanup of file descriptor/fork management with tons of help
136
- from skaar and ezra. thanks guys!
137
-
138
- - introduced Slave.object method used to return any object directory from
139
- a child process. see samples/g.rb.
140
-
141
- - indroduced keyword to automatically make slave objects threadsafe.
142
- remember that your slave object must be threadsafe because they are
143
- being server via DRb!!!
144
-
145
- 1.0.0:
146
- - THIS RELEASE IS !! NOT !! BACKWARD COMPATIBLE. NOTE NEW CTOR SYNTAX.
147
-
148
- - detach method also sets up at_exit handler. extra protection from
149
- zombies.
150
-
151
- - ezra zygmuntowicz asked for a feature whereby a parent could be notified
152
- when a child exited. obviously such a mechanism should be both async
153
- and sync. to accomplish this the wait method was extended to support a
154
- callback with is either sync or async
155
-
156
- slave = Server.new{ Server.new }
157
-
158
- slave.wait and puts 'this is sync!'
159
-
160
- slave.wait(:non_block=&gt;true){ 'this is async!' }
161
-
162
- - patch to getval from skaar&lt;skaar@waste.org&gt;. the impl dropped opts
163
- delgating to the class method from the instance one.
164
-
165
- 0.2.0:
166
- incorporated joel vanderWerf's patch such that, if no object is passed the
167
- block is used to create one ONLY in the child. this avoids having a copy
168
- in both parent and child is that needs to be avoided due to, for instance,
169
- resource consumption.
170
-
171
- 0.0.1:
172
- - patch from Logan Capaldo adds block form to slave new, block is run in the
173
- child
174
-
175
- - added a few more samples/*
176
-
177
- - added Slave#wait
178
-
179
- - added status information to slaves
180
-
181
- - added close-on-exec flag to pipes in parent process
182
-
183
- 0.0.0:
184
- - initial version
185
- </pre>
186
- <p>
187
- SAMPLES
188
- </p>
189
- <pre>
190
- &lt;========&lt; samples/a.rb &gt;========&gt;
191
-
192
- ~ &gt; cat samples/a.rb
193
-
194
- require 'slave'
195
- #
196
- # simple usage is simply to stand up a server object as a slave. you do not
197
- # need to wait for the server, join it, etc. it will die when the parent
198
- # process dies - even under 'kill -9' conditions
199
- #
200
- class Server
201
- def add_two n
202
- n + 2
203
- end
204
- end
205
-
206
- slave = Slave.new :object =&gt; Server.new
207
-
208
- server = slave.object
209
- p server.add_two(40) #=&gt; 42
210
-
211
- slave.shutdown
212
-
213
- ~ &gt; ruby samples/a.rb
214
-
215
- 42
216
-
217
- &lt;========&lt; samples/b.rb &gt;========&gt;
218
-
219
- ~ &gt; cat samples/b.rb
220
-
221
- require 'slave'
222
- #
223
- # if certain operations need to take place in the child only a block can be
224
- # used
225
- #
226
- class Server
227
- def connect_to_db
228
- &quot;we only want to do this in the child process!&quot;
229
- @connection = :postgresql
230
- end
231
- attr :connection
232
- end
233
-
234
- slave = Slave.new('object' =&gt; Server.new){|s| s.connect_to_db}
235
-
236
- server = slave.object
237
-
238
- p server.connection #=&gt; :postgresql
239
- #
240
- # errors in the child are detected and raised in the parent
241
- #
242
- slave = Slave.new('object' =&gt; Server.new){|s| s.typo} #=&gt; raises an error!
243
-
244
- ~ &gt; ruby samples/b.rb
245
-
246
- :postgresql
247
- samples/b.rb:22: undefined method `typo' for #&lt;Server:0xb756ed18&gt; (NoMethodError)
248
- from ./lib/slave.rb:369:in `[]'
249
- from ./lib/slave.rb:369:in `initialize'
250
- from samples/b.rb:22:in `new'
251
- from samples/b.rb:22
252
-
253
- &lt;========&lt; samples/c.rb &gt;========&gt;
254
-
255
- ~ &gt; cat samples/c.rb
256
-
257
- require 'slave'
258
- #
259
- # if no slave object is given the block itself is used to contruct it
260
- #
261
- class Server
262
- def initialize
263
- &quot;this is run only in the child&quot;
264
- @pid = Process.pid
265
- end
266
- attr 'pid'
267
- end
268
-
269
- slave = Slave.new{ Server.new }
270
- server = slave.object
271
-
272
- p Process.pid
273
- p server.pid # not going to be the same as parents!
274
- #
275
- # errors are still detected though
276
- #
277
- slave = Slave.new{ fubar } # raises error in parent
278
-
279
- ~ &gt; ruby samples/c.rb
280
-
281
- 7971
282
- 7972
283
- samples/c.rb:21: undefined local variable or method `fubar' for main:Object (NameError)
284
- from ./lib/slave.rb:361:in `call'
285
- from ./lib/slave.rb:361:in `initialize'
286
- from samples/c.rb:21:in `new'
287
- from samples/c.rb:21
288
-
289
- &lt;========&lt; samples/d.rb &gt;========&gt;
290
-
291
- ~ &gt; cat samples/d.rb
292
-
293
- require 'slave'
294
- #
295
- # at_exit hanlders are handled correctly in both child and parent
296
- #
297
- at_exit{ p 'parent' }
298
- slave = Slave.new{ at_exit{ p 'child' }; 'the server is this string' }
299
- #
300
- # this will print 'child', then 'parent'
301
- #
302
-
303
- ~ &gt; ruby samples/d.rb
304
-
305
- &quot;child&quot;
306
- &quot;parent&quot;
307
-
308
- &lt;========&lt; samples/e.rb &gt;========&gt;
309
-
310
- ~ &gt; cat samples/e.rb
311
-
312
- require 'slave'
313
- #
314
- # slaves never outlive their parent. if the parent exits, even under kill -9,
315
- # the child will die.
316
- #
317
- slave = Slave.new{ at_exit{ p 'child' }; 'the server is this string' }
318
-
319
- Process.kill brutal=9, the_parent_pid=Process.pid
320
- #
321
- # even though parent dies a nasty death the child will still print 'child'
322
- #
323
-
324
- ~ &gt; ruby samples/e.rb
325
-
326
- &quot;child&quot;
327
-
328
- &lt;========&lt; samples/f.rb &gt;========&gt;
329
-
330
- ~ &gt; cat samples/f.rb
331
-
332
- require 'slave'
333
- #
334
- # slaves created previously are visible to newly created slaves - in this
335
- # example the child process of slave_a communicates directly with the child
336
- # process of slave_a
337
- #
338
- slave_a = Slave.new{ Array.new }
339
- slave_b = Slave.new{ slave_a.object }
340
-
341
- a, b = slave_b.object, slave_a.object
342
-
343
- b &lt;&lt; 42
344
- puts a #=&gt; 42
345
-
346
- ~ &gt; ruby samples/f.rb
347
-
348
- 42
349
-
350
- &lt;========&lt; samples/g.rb &gt;========&gt;
351
-
352
- ~ &gt; cat samples/g.rb
353
-
354
- require 'slave'
355
- #
356
- # Slave.object can used when you want to construct an object in another
357
- # process. in otherwords you want to fork a process and retrieve a single
358
- # returned object from that process as opposed to setting up a server.
359
- #
360
- this = Process.pid
361
- that = Slave.object{ Process.pid }
362
-
363
- p 'this' =&gt; this, 'that' =&gt; that
364
-
365
- #
366
- # any object can be returned and it can be returned asychronously via a thread
367
- #
368
- thread = Slave.object(:async =&gt; true){ sleep 2 and [ Process.pid, Time.now ] }
369
- this = [ Process.pid, Time.now ]
370
- that = thread.value
371
-
372
- p 'this' =&gt; this, 'that' =&gt; that
373
-
374
- ~ &gt; ruby samples/g.rb
375
-
376
- {&quot;that&quot;=&gt;7990, &quot;this&quot;=&gt;7989}
377
- {&quot;that&quot;=&gt;[7991, Fri, Apr 27 2007 16:38:30 -0600], &quot;this&quot;=&gt;[7989, Fri, Apr 27 2007 16:38:28 -0600]}
378
- </pre>
379
-
380
- </div>
381
-
382
-
383
- </div>
384
-
385
-
386
- </div>
387
-
388
-
389
- <!-- if includes -->
390
-
391
- <div id="section">
392
-
393
-
394
-
395
-
396
-
397
-
398
-
399
-
400
- <!-- if method_list -->
401
-
402
-
403
- </div>
404
-
405
-
406
- <div id="validator-badges">
407
- <p><small><a href="http://validator.w3.org/check/referer">[Validate]</a></small></p>
408
- </div>
409
-
410
- </body>
411
- </html>