class XRBP::WebSocket::Socket
Low level wrapper around TCPSocket operations, providing mechanisms to negotiate base websocket connection.
@private
Constants
- DEFAULT_PORTS
Attributes
client[RW]
pipe_broken[R]
socket[R]
Public Class Methods
new(client)
click to toggle source
# File lib/xrbp/websocket/socket.rb, line 32 def initialize(client) @client = client @pipe_broken = false end
Public Instance Methods
close()
click to toggle source
# File lib/xrbp/websocket/socket.rb, line 75 def close socket.close if socket end
connect()
click to toggle source
# File lib/xrbp/websocket/socket.rb, line 37 def connect uri = URI.parse client.url host = uri.host port = uri.port || DEFAULT_PORTS[uri.scheme.intern] @socket = TCPSocket.new(host, port) socket.setsockopt(::Socket::IPPROTO_TCP, ::Socket::TCP_NODELAY, 1) init_ssl_socket if ['https', 'wss'].include? uri.scheme nil end
options()
click to toggle source
# File lib/xrbp/websocket/socket.rb, line 28 def options client.options end
read_next(dest)
click to toggle source
# File lib/xrbp/websocket/socket.rb, line 105 def read_next(dest) begin read_sockets, _, _ = IO.select([socket], nil, nil, 0.1) if read_sockets && read_sockets[0] dest << socket.read_nonblock(1024) if socket.respond_to?(:pending) # SSLSocket dest << socket.read(socket.pending) while socket.pending > 0 end end rescue IO::WaitReadable # No op rescue IO::WaitWritable IO.select(nil, [socket]) retry end end
write(data)
click to toggle source
# File lib/xrbp/websocket/socket.rb, line 79 def write(data) socket.write data end
write_nonblock(data)
click to toggle source
# File lib/xrbp/websocket/socket.rb, line 83 def write_nonblock(data) begin socket.write_nonblock(data) rescue IO::WaitReadable IO.select([socket]) # OpenSSL needs to read internally retry rescue IO::WaitWritable, Errno::EINTR IO.select(nil, [socket]) retry rescue Errno::EPIPE => e @pipe_broken = true raise rescue OpenSSL::SSL::SSLError => e @pipe_broken = true raise end end
Private Instance Methods
init_ssl_socket()
click to toggle source
# File lib/xrbp/websocket/socket.rb, line 51 def init_ssl_socket ssl_context = options[:ssl_context] || begin ctx = OpenSSL::SSL::SSLContext.new ctx.ssl_version = options[:ssl_version] || 'SSLv23' # use VERIFY_PEER for verification: ctx.verify_mode = options[:verify_mode] || OpenSSL::SSL::VERIFY_NONE cert_store = OpenSSL::X509::Store.new cert_store.set_default_paths ctx.cert_store = cert_store ctx end @socket = ::OpenSSL::SSL::SSLSocket.new(socket, ssl_context) socket.connect end