davebryson (owner)

Revisions

gist: 101187 Download_button fork
public
Description:
Example of talking to Erlang's epmd from Ruby
Public Clone URL: git://gist.github.com/101187.git
Embed All Files: show embed
ruby_2_epmd.rb #
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
# Example of connecting to Epmd to get the port number
# of an Erlang node
require 'rubygems'
require 'eventmachine'
 
class EpmdConnection < EM::Connection
  include EM::Deferrable
  attr_accessor :nodename
  
  def self.lookup_node(nodename)
    EM.connect("127.0.0.1",4369,EpmdConnection) do |conn|
      conn.nodename = nodename
    end
  end
  
  def connection_completed
    send_data lookup_port
  end
  
  def receive_data(data)
    parse_response(data)
  end
  
  def unbind
    puts "Done"
  end
  
  def lookup_port
    out = StringIO.new('', 'w')
    
    # Create the header with length: 2
    out.write([@nodename.size + 1].pack('n'))
    
    # Next the request
    # tag. Length: 1
    out.write([122].pack("C"))
    # nodename
    out.write(nodename)
    out.string
  end
  
  # If we get a good result we only return
  # the port (not reading all the information
  def parse_response(input)
    i = StringIO.new(input)
    code = i.read(1).unpack('C').first
    result = i.read(1).unpack('C').first
    if result == 0
      # good response read the port
      port = i.read(2).unpack('n').first
      set_deferred_success "port for #{@nodename} is #{port}"
    else
      set_deferred_failure "bad result code"
    end
  end
end
 
EM.run do
  # Make sure you start an Erlang node: 'erl -sname hello'
  epmd = EpmdConnection.lookup_node("hello")
  epmd.callback do |resp|
    puts "Got: #{resp}"
    EM.stop
  end
  epmd.errback do |err|
    puts "Error: #{err}"
    EM.stop
  end
end