Class: EventMachine::Protocols::HeaderAndContentProtocol
- Inherits:
-
Connection
- Object
- Connection
- EventMachine::Protocols::HeaderAndContentProtocol
- Includes:
- LineText2
- Defined in:
- lib/em/protocols/header_and_content.rb
Overview
Usage
class RequestHandler < EM::P::HeaderAndContentProtocol
def receive_request headers, content
p [:request, headers, content]
end
end
EM.run{
EM.start_server 'localhost', 80, RequestHandler
}
– Originally, this subclassed LineAndTextProtocol, which in turn relies on BufferedTokenizer, which doesn’t gracefully handle the transitions between lines and binary text. Changed 13Sep08 by FCianfrocca.
Constant Summary collapse
- ContentLengthPattern =
/Content-length:\s*(\d+)/i
Constants included from LineText2
Instance Attribute Summary
Attributes inherited from Connection
Class Method Summary collapse
Instance Method Summary collapse
-
#headers_2_hash(hdrs) ⇒ Object
Basically a convenience method.
-
#initialize(*args) ⇒ HeaderAndContentProtocol
constructor
A new instance of HeaderAndContentProtocol.
- #receive_binary_data(text) ⇒ Object
- #receive_line(line) ⇒ Object
Methods included from LineText2
#receive_data, #receive_end_of_binary_data, #set_binary_mode, #set_delimiter, #set_line_mode, #set_text_mode, #unbind
Methods inherited from Connection
#associate_callback_target, #close_connection, #close_connection_after_writing, #comm_inactivity_timeout, #comm_inactivity_timeout=, #connection_completed, #detach, #error?, #get_cipher_bits, #get_cipher_name, #get_cipher_protocol, #get_idle_time, #get_outbound_data_size, #get_peer_cert, #get_peername, #get_pid, #get_proxied_bytes, #get_sni_hostname, #get_sock_opt, #get_sockname, #get_status, new, #notify_readable=, #notify_readable?, #notify_writable=, #notify_writable?, #pause, #paused?, #pending_connect_timeout, #pending_connect_timeout=, #post_init, #proxy_completed, #proxy_incoming_to, #proxy_target_unbound, #receive_data, #reconnect, #resume, #send_data, #send_datagram, #send_file_data, #set_sock_opt, #ssl_handshake_completed, #ssl_verify_peer, #start_tls, #stop_proxying, #stream_file_data, #unbind
Constructor Details
#initialize(*args) ⇒ HeaderAndContentProtocol
Returns a new instance of HeaderAndContentProtocol.
51 52 53 54 |
# File 'lib/em/protocols/header_and_content.rb', line 51 def initialize *args super init_for_request end |
Class Method Details
.headers_2_hash(hdrs) ⇒ Object
124 125 126 127 128 129 130 131 132 133 |
# File 'lib/em/protocols/header_and_content.rb', line 124 def headers_2_hash hdrs hash = {} hdrs.each {|h| if /\A([^\s:]+)\s*:\s*/ =~ h tail = $'.dup hash[ $1.downcase.gsub(/-/,"_").intern ] = tail end } hash end |
Instance Method Details
#headers_2_hash(hdrs) ⇒ Object
Basically a convenience method. We might create a subclass that does this automatically. But it’s such a performance killer.
119 120 121 |
# File 'lib/em/protocols/header_and_content.rb', line 119 def headers_2_hash hdrs self.class.headers_2_hash hdrs end |
#receive_binary_data(text) ⇒ Object
92 93 94 95 |
# File 'lib/em/protocols/header_and_content.rb', line 92 def receive_binary_data text @hc_content = text dispatch_request end |
#receive_line(line) ⇒ Object
56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 |
# File 'lib/em/protocols/header_and_content.rb', line 56 def receive_line line case @hc_mode when :discard_blanks unless line == "" @hc_mode = :headers receive_line line end when :headers if line == "" raise "unrecognized state" unless @hc_headers.length > 0 if respond_to?(:receive_headers) receive_headers @hc_headers end # @hc_content_length will be nil, not 0, if there was no content-length header. if @hc_content_length.to_i > 0 set_binary_mode @hc_content_length else dispatch_request end else @hc_headers << line if ContentLengthPattern =~ line # There are some attacks that rely on sending multiple content-length # headers. This is a crude protection, but needs to become tunable. raise "extraneous content-length header" if @hc_content_length @hc_content_length = $1.to_i end if @hc_headers.length == 1 and respond_to?(:receive_first_header_line) receive_first_header_line line end end else raise "internal error, unsupported mode" end end |