Class: Pione::Relay::RelaySocket
- Inherits:
-
DRb::DRbSSLSocket
- Object
- DRb::DRbSSLSocket
- Pione::Relay::RelaySocket
- Defined in:
- lib/pione/relay/relay-socket.rb
Overview
RelaySocket is connection layer between PIONE client and PIONE relay.
Defined Under Namespace
Classes: AuthError, BadMessage, ProxyError
Class Method Summary collapse
-
.open(uri, config) ⇒ Object
Opens the socket on pione-client.
-
.open_server(uri, config) ⇒ Object
private
Opens relay server port for clients.
- .parse_uri(uri) ⇒ Object
- .uri_option(uri, config) ⇒ Object
Instance Method Summary collapse
-
#accept ⇒ Object
private
Accepts pione-clients on server side.
-
#create_proxy_server(transmitter_id) ⇒ Object
Creates a proxy server for brokers in LAN.
-
#create_transmitter_server(transmitter_id) ⇒ void
Creates a transmitter server with the relay socket.
Class Method Details
.open(uri, config) ⇒ Object
Opens the socket on pione-client.
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 70 71 72 73 74 75 |
# File 'lib/pione/relay/relay-socket.rb', line 27 def self.open(uri, config) host, port, option = parse_uri(uri) host.untaint port.untaint # make tcp connection with SSL soc = TCPSocket.open(host, port) ssl_conf = DRb::DRbSSLSocket::SSLConfig.new(config) ssl_conf.setup_ssl_context ssl = ssl_conf.connect(soc) if Global.show_communication puts "you connected relay socket to %s" % uri end # auth like HTTP's digest method begin Timeout.timeout(Global.relay_client_auth_timeout_sec) do realm = ssl.gets.chomp uuid = ssl.gets.chomp account = Global.relay_account_db[realm] || (raise AuthError.new("unknown realm: %s" % realm)) name = account.name digest = account.digest response = "%s:%s" % [name, Digest::SHA512.hexdigest("%s:%s" % [uuid, digest])] ssl.puts(response) unless ssl.read(3).chomp == "OK" raise AuthError.new("authentication failed") end end rescue AuthError => e raise e rescue Timeout::Error raise AuthError.new("authentication timeout") end if Global.show_communication puts "you succeeded relay authentication: %s" % uri end # create receiver socket ReceiverSocket.table["%s:%s" % [host, port]] = ssl Global.relay_receiver = DRb::DRbServer.new( "receiver://%s:%s" % [host, port], Global.relay_tuple_space_server ) # create an instance return self.new(uri, ssl, ssl_conf, true) end |
.open_server(uri, config) ⇒ Object
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
Opens relay server port for clients.
79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 |
# File 'lib/pione/relay/relay-socket.rb', line 79 def self.open_server(uri, config) # parse URI uri = 'relay://:%s' % Global.relay_port unless uri host, port, option = parse_uri(uri) # rebuild URI if host.size == 0 host = getservername soc = open_server_inaddr_any(host, port) else soc = TCPServer.open(host, port) end port = soc.addr[1] if port == 0 new_uri = "relay://#{host}:#{port}" # prepare SSL ssl_conf = DRb::DRbSSLSocket::SSLConfig.new(config).tap do |conf| conf.setup_certificate conf.setup_ssl_context end # create instance self.new(new_uri, soc, ssl_conf, false) end |
.parse_uri(uri) ⇒ Object
14 15 16 17 18 19 20 21 22 23 24 |
# File 'lib/pione/relay/relay-socket.rb', line 14 def self.parse_uri(uri) if uri =~ /^relay:\/\/(.*?)(:(\d+))?(\?(.*))?$/ host = $1 port = $3 ? $3.to_i : Global.relay_port option = $5 return host, port, option else raise DRb::DRbBadScheme.new(uri) unless uri =~ /^relay:/ raise DRb::DRbBadURI.new('can\'t parse uri:' + uri) end end |
.uri_option(uri, config) ⇒ Object
104 105 106 107 |
# File 'lib/pione/relay/relay-socket.rb', line 104 def self.uri_option(uri, config) host, port, option = parse_uri(uri) return "relay://#{host}:#{port}", option end |
Instance Method Details
#accept ⇒ Object
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
Accepts pione-clients on server side.
111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 |
# File 'lib/pione/relay/relay-socket.rb', line 111 def accept begin # accept loop while true soc = @socket.accept break if (@acl ? @acl.allow_socket?(soc) : true) soc.close end if Global.show_communication puts "someone connected to relay socket..." end # build ssl ssl = @config.accept(soc) # relay auth like HTTP's digest method ssl.puts(Global.relay_realm) uuid = Util::UUID.generate ssl.puts(uuid) if msg = ssl.gets name, digest = msg.chomp.split(":") unless Global.relay_client_db.auth(uuid, name, digest) raise AuthError.new(name) end ssl.puts "OK" if Global.show_communication puts "succeeded authentication for %s" % name end # setup transmitter_id transmitter_id = Util::UUID.generate # save ssl socket as receiver side with transmitter_id TransmitterSocket.receiver_socket[transmitter_id] = ssl # open and save tcp socket with transmitter_id Global.relay_transmitter_proxy_side_port_range.each do |port| begin tcp_socket = TCPServer.new("localhost", port) TransmitterSocket.proxy_socket[transmitter_id] = tcp_socket break rescue end end # create servers transmitter_server = create_transmitter_server(transmitter_id) proxy_server = create_proxy_server(transmitter_id) # start to provide the proxy server TupleSpaceProvider.instance.add_tuple_space_server( DRb::DRbObject.new_with_uri(proxy_server.uri) ) # create instance self.class.new(uri, ssl, @config, true) else raise BadMessage end rescue OpenSSL::SSL::SSLError, AuthError, BadMessage => e soc.close Log::Debug.communication("relay socket was closed: %s" % e.) retry end end |
#create_proxy_server(transmitter_id) ⇒ Object
Creates a proxy server for brokers in LAN.
191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 |
# File 'lib/pione/relay/relay-socket.rb', line 191 def create_proxy_server(transmitter_id) transmitter = DRb::DRbObject.new_with_uri("transmitter://%s" % transmitter_id) Global.relay_proxy_port_range.each do |port| begin uri = "druby://localhost:%s" % port server = DRb::DRbServer.new(uri, transmitter) if Global.show_communication puts "relay created the proxy: %s" % server.uri end return server rescue next end end raise ProxyError.new("You cannot start relay proxy server.") end |
#create_transmitter_server(transmitter_id) ⇒ void
This method returns an undefined value.
Creates a transmitter server with the relay socket.
181 182 183 184 185 186 187 188 |
# File 'lib/pione/relay/relay-socket.rb', line 181 def create_transmitter_server(transmitter_id) uri = "transmitter://%s" % transmitter_id server = DRb::DRbServer.new(uri, Trampoline.new(uri, @config)) if Global.show_communication puts "relay created the transmitter: %s" % server.uri end return server end |