class Mongrel2::WebSocketRequestFactory

A factory for generating WebSocket request objects for testing.

Constants

DEFAULT_FACTORY_CONFIG

The defaults used by the websocket request factory

DEFAULT_HANDSHAKE_BODY
DEFAULT_TESTING_HEADERS

Default headers

DEFAULT_TESTING_HOST

The default host

DEFAULT_TESTING_PORT
DEFAULT_TESTING_ROUTE

Public Instance Methods

binary( uri, payload='', *flags ) click to toggle source

Create a binary frame.

# File lib/mongrel2/testing.rb, line 385
def binary( uri, payload='', *flags )
        flags << :binary
        return self.create( uri, payload, flags )
end
close( uri, payload='', *flags ) click to toggle source

Create a close frame.

# File lib/mongrel2/testing.rb, line 392
def close( uri, payload='', *flags )
        flags << :close << :fin
        return self.create( uri, payload, flags )
end
continuation( uri, payload='', *flags ) click to toggle source

Create a continuation frame.

# File lib/mongrel2/testing.rb, line 371
def continuation( uri, payload='', *flags )
        flags << :continuation
        return self.create( uri, payload, flags )
end
create( uri, data, *flags ) click to toggle source

Create a new request with the specified uri, data, and flags.

# File lib/mongrel2/testing.rb, line 357
def create( uri, data, *flags )
        raise "Request doesn't route through %p" % [ self.route ] unless
                uri.start_with?( self.route )

        headers = if flags.last.is_a?( Hash ) then flags.pop else {} end
        flagheader = make_flags_header( flags )
        headers = self.make_merged_headers( uri, flagheader, headers )
        rclass = Mongrel2::Request.subclass_for_method( :WEBSOCKET )

        return rclass.new( self.sender_id, self.conn_id.to_s, self.route, headers, data )
end
handshake( uri, *subprotocols ) click to toggle source

Create an initial websocket handshake request and return it.

# File lib/mongrel2/testing.rb, line 337
def handshake( uri, *subprotocols )
        raise "Request doesn't route through %p" % [ self.route ] unless
                uri.start_with?( self.route )

        headers = if subprotocols.last.is_a?( Hash ) then subprotocols.pop else {} end
        headers = self.make_merged_headers( uri, 0, headers )
        headers.delete( :flags )

        unless subprotocols.empty?
                protos = subprotocols.map( &:to_s ).join( ', ' )
                headers.sec_websocket_protocol = protos
        end

        rclass = Mongrel2::Request.subclass_for_method( :WEBSOCKET_HANDSHAKE )

        return rclass.new( self.sender_id, self.conn_id.to_s, self.route, headers, DEFAULT_HANDSHAKE_BODY.dup )
end
ping( uri, payload='', *flags ) click to toggle source

Create a ping frame.

# File lib/mongrel2/testing.rb, line 399
def ping( uri, payload='', *flags )
        flags << :ping << :fin
        return self.create( uri, payload, flags )
end
pong( uri, payload='', *flags ) click to toggle source

Create a pong frame.

# File lib/mongrel2/testing.rb, line 406
def pong( uri, payload='', *flags )
        flags << :pong << :fin
        return self.create( uri, payload, flags )
end
text( uri, payload='', *flags ) click to toggle source

Create a text frame.

# File lib/mongrel2/testing.rb, line 378
def text( uri, payload='', *flags )
        flags << :text
        return self.create( uri, payload, flags )
end

Protected Instance Methods

make_merged_headers( uri, flags, userheaders ) click to toggle source

Merge the factory's headers with userheaders, and then merge in the special headers that Mongrel2 adds that are based on the uri and other server attributes.

# File lib/mongrel2/testing.rb, line 420
def make_merged_headers( uri, flags, userheaders )
        headers = self.headers.merge( userheaders )
        uri = URI( uri )

        # Add mongrel headers
        headers.uri       = uri.to_s
        headers.path      = uri.path
        headers.host      = "%s:%d" % [ self.host, self.port ]
        headers.query     = uri.query if uri.query
        headers.pattern   = self.route
        headers.origin    = "http://#{headers.host}"
        headers.flags     = "0x%02x" % [ flags ]

        self.log.debug "Headers are: %p" % [ headers ]

        return headers
end

Private Instance Methods

make_flags_header( *flag_symbols ) click to toggle source

Make a flags value out of flag Symbols that correspond to the flag bits and opcodes: [ :fin, :rsv1, :rsv2, :rsv3, :continuation, :text, :binary, :close, :ping, :pong ]. If the flags contain Integers instead, they are ORed with the result.

# File lib/mongrel2/testing.rb, line 447
def make_flags_header( *flag_symbols )
        flag_symbols.flatten!
        flag_symbols.compact!

        self.log.debug "Making a flags header for symbols: %p" % [ flag_symbols ]

        return flag_symbols.inject( 0x00 ) do |flags, flag|
                case flag
                when :fin
                        flags | WebSocket::FIN_FLAG
                when :rsv1
                        flags | WebSocket::RSV1_FLAG
                when :rsv2
                        flags | WebSocket::RSV2_FLAG
                when :rsv3
                        flags | WebSocket::RSV3_FLAG
                when :continuation, :text, :binary, :close, :ping, :pong
                        # Opcodes clear any other opcodes present
                        flags ^= ( flags & WebSocket::OPCODE_BITMASK )
                        flags | WebSocket::OPCODE[ flag ]
                when Integer
                        flags | flag
                else
                        raise ArgumentError, "Don't know what the %p flag is." % [ flag ]
                end
        end
end