| Class | Rinda::RingFinger |
| In: |
lib/rinda/ring.rb
|
| Parent: | Object |
RingFinger is used by RingServer clients to discover the RingServer‘s TupleSpace. Typically, all a client needs to do is call RingFinger.primary to retrieve the remote TupleSpace, which it can then begin using.
| broadcast_list | [RW] | The list of addresses where RingFinger will send query packets. |
| port | [RW] | The port that RingFinger will send query packets to. |
| primary | [RW] | Contain the first advertised TupleSpace after lookup_ring_any is called. |
Creates a singleton RingFinger and looks for a RingServer. Returns the created RingFinger.
# File lib/rinda/ring.rb, line 106
106: def self.finger
107: unless @@finger
108: @@finger = self.new
109: @@finger.lookup_ring_any
110: end
111: @@finger
112: end
Creates a new RingFinger that will look for RingServers at port on the addresses in broadcast_list.
# File lib/rinda/ring.rb, line 147
147: def initialize(broadcast_list=@@broadcast_list, port=Ring_PORT)
148: @broadcast_list = broadcast_list || ['localhost']
149: @port = port
150: @primary = nil
151: @rings = []
152: end
Returns the first advertised TupleSpace.
# File lib/rinda/ring.rb, line 117
117: def self.primary
118: finger.primary
119: end
Looks up RingServers waiting timeout seconds. RingServers will be given block as a callback, which will be called with the remote TupleSpace.
# File lib/rinda/ring.rb, line 176
176: def lookup_ring(timeout=5, &block)
177: return lookup_ring_any(timeout) unless block_given?
178:
179: msg = Marshal.dump([[:lookup_ring, DRbObject.new(block)], timeout])
180: @broadcast_list.each do |it|
181: soc = UDPSocket.open
182: begin
183: soc.setsockopt(Socket::SOL_SOCKET, Socket::SO_BROADCAST, true)
184: soc.send(msg, 0, it, @port)
185: rescue
186: nil
187: ensure
188: soc.close
189: end
190: end
191: sleep(timeout)
192: end
Returns the first found remote TupleSpace. Any further recovered TupleSpaces can be found by calling to_a.
# File lib/rinda/ring.rb, line 198
198: def lookup_ring_any(timeout=5)
199: queue = Queue.new
200:
201: th = Thread.new do
202: self.lookup_ring(timeout) do |ts|
203: queue.push(ts)
204: end
205: queue.push(nil)
206: while it = queue.pop
207: @rings.push(it)
208: end
209: end
210:
211: @primary = queue.pop
212: raise('RingNotFound') if @primary.nil?
213: @primary
214: end