class EventMachine::Protocols::HeaderAndContentProtocol
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 }
Constants
- ContentLengthPattern
Public Class Methods
headers_2_hash(hdrs)
click to toggle source
# 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
new(*args)
click to toggle source
Calls superclass method
EventMachine::Connection::new
# File lib/em/protocols/header_and_content.rb, line 51 def initialize *args super init_for_request end
Public Instance Methods
headers_2_hash(hdrs)
click to toggle source
Basically a convenience method. We might create a subclass that does this automatically. But it’s such a performance killer.
# 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)
click to toggle source
# File lib/em/protocols/header_and_content.rb, line 92 def receive_binary_data text @hc_content = text dispatch_request end
receive_line(line)
click to toggle source
# 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
Private Instance Methods
dispatch_request()
click to toggle source
# File lib/em/protocols/header_and_content.rb, line 97 def dispatch_request if respond_to?(:receive_request) receive_request @hc_headers, @hc_content end init_for_request end
init_for_request()
click to toggle source
# File lib/em/protocols/header_and_content.rb, line 105 def init_for_request @hc_mode = :discard_blanks @hc_headers = [] # originally was @hc_headers ||= []; @hc_headers.clear to get a performance # boost, but it's counterproductive because a subclassed handler will have to # call dup to use the header array we pass in receive_headers. @hc_content_length = nil @hc_content = "" end