summaryrefslogtreecommitdiff
path: root/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec
diff options
context:
space:
mode:
Diffstat (limited to 'vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec')
-rw-r--r--vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/parser_spec.rb428
-rw-r--r--vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/spec_helper.rb1
-rw-r--r--vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/support/requests.json612
-rw-r--r--vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/support/responses.json395
4 files changed, 1436 insertions, 0 deletions
diff --git a/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/parser_spec.rb b/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/parser_spec.rb
new file mode 100644
index 0000000..9277c0f
--- /dev/null
+++ b/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/parser_spec.rb
@@ -0,0 +1,428 @@
+if defined?(Encoding)
+ Encoding.default_external = "UTF-8"
+end
+require "spec_helper"
+require "json"
+
+describe HTTP::Parser do
+ before do
+ @parser = HTTP::Parser.new
+
+ @headers = nil
+ @body = ""
+ @started = false
+ @done = false
+
+ @parser.on_message_begin = proc{ @started = true }
+ @parser.on_headers_complete = proc { |e| @headers = e }
+ @parser.on_body = proc { |chunk| @body << chunk }
+ @parser.on_message_complete = proc{ @done = true }
+ end
+
+ it "should have initial state" do
+ expect(@parser.headers).to be_nil
+
+ expect(@parser.http_version).to be_nil
+ expect(@parser.http_method).to be_nil
+ expect(@parser.status_code).to be_nil
+
+ expect(@parser.request_url).to be_nil
+
+ expect(@parser.header_value_type).to eq(:mixed)
+ end
+
+ it "should be able to run in non-main ractors" do
+ skip unless Kernel.const_defined?(:Ractor)
+ default_header_value_type = HTTP::Parser.default_header_value_type
+ r = Ractor.new(default_header_value_type) { |type|
+ parser = HTTP::Parser.new(default_header_value_type: type)
+ done = false
+ parser.on_message_complete = proc {
+ done = true
+ }
+ parser <<
+ "GET /ractor HTTP/1.1\r\n" +
+ "Content-Length: 5\r\n" +
+ "\r\n" +
+ "World"
+ done
+ }
+ expect(r.take).to be true
+ end
+
+ it "should allow us to set the header value type" do
+ [:mixed, :arrays, :strings].each do |type|
+ @parser.header_value_type = type
+ expect(@parser.header_value_type).to eq(type)
+
+ parser_tmp = HTTP::Parser.new(nil, type)
+ expect(parser_tmp.header_value_type).to eq(type)
+
+ parser_tmp2 = HTTP::Parser.new(default_header_value_type: type)
+ expect(parser_tmp2.header_value_type).to eq(type)
+ end
+ end
+
+ it "should allow us to set the default header value type" do
+ [:mixed, :arrays, :strings].each do |type|
+ HTTP::Parser.default_header_value_type = type
+
+ parser = HTTP::Parser.new
+ expect(parser.header_value_type).to eq(type)
+ end
+ end
+
+ it "should throw an Argument Error if header value type is invalid" do
+ expect{ @parser.header_value_type = 'bob' }.to raise_error(ArgumentError)
+ end
+
+ it "should throw an Argument Error if default header value type is invalid" do
+ expect{ HTTP::Parser.default_header_value_type = 'bob' }.to raise_error(ArgumentError)
+ end
+
+ it "should implement basic api" do
+ @parser <<
+ "GET /test?ok=1 HTTP/1.1\r\n" +
+ "User-Agent: curl/7.18.0\r\n" +
+ "Host: 0.0.0.0:5000\r\n" +
+ "Accept: */*\r\n" +
+ "Content-Length: 5\r\n" +
+ "\r\n" +
+ "World"
+
+ expect(@started).to be true
+ expect(@done).to be true
+
+ expect(@parser.http_major).to eq(1)
+ expect(@parser.http_minor).to eq(1)
+ expect(@parser.http_version).to eq([1,1])
+ expect(@parser.http_method).to eq('GET')
+ expect(@parser.status_code).to be_nil
+
+ expect(@parser.request_url).to eq('/test?ok=1')
+
+ expect(@parser.headers).to eq(@headers)
+ expect(@parser.headers['User-Agent']).to eq('curl/7.18.0')
+ expect(@parser.headers['Host']).to eq('0.0.0.0:5000')
+
+ expect(@body).to eq("World")
+ end
+
+ it "should raise errors on invalid data" do
+ expect{ @parser << "BLAH" }.to raise_error(HTTP::Parser::Error)
+ end
+
+ it "should abort parser via header complete callback with a body" do
+ @parser.on_headers_complete = proc { |e| @headers = e; :stop }
+
+ data =
+ "GET / HTTP/1.0\r\n" +
+ "Content-Length: 5\r\n" +
+ "\r\n" +
+ "World"
+
+ bytes = @parser << data
+
+ expect(bytes).to eq(37)
+ expect(data[bytes..-1]).to eq('World')
+
+ expect(@headers).to eq({'Content-Length' => '5'})
+ expect(@body).to be_empty
+ expect(@done).to be false
+ end
+
+ it "should abort parser via header complete callback without a body" do
+ @parser.on_headers_complete = proc { |e| @headers = e; :stop }
+
+ data =
+ "GET / HTTP/1.0\r\n" +
+ "Content-Length: 0\r\n" +
+ "\r\n"
+
+ bytes = @parser << data
+
+ expect(bytes).to eq(37)
+ expect(data[bytes..-1]).to eq('')
+
+ expect(@headers).to eq({'Content-Length' => '0'})
+ expect(@body).to be_empty
+ expect(@done).to be false
+ end
+
+ it "should abort parser via message complete callback with a body" do
+ @parser.on_message_complete = proc { :stop }
+
+ data =
+ "CONNECT www.example.com:443 HTTP/1.0\r\n" +
+ "Connection: keep-alive\r\n" +
+ "\r\n" +
+ "World"
+
+ bytes = @parser << data
+
+ expect(bytes).to eq(64)
+ expect(data[bytes..-1]).to eq('World')
+
+ expect(@headers).to eq({'Connection' => 'keep-alive'})
+ expect(@parser.upgrade_data).to eq('World')
+ expect(@body).to be_empty
+ expect(@done).to be false
+ end
+
+ it "should abort parser via message complete callback without a body" do
+ @parser.on_message_complete = proc { :stop }
+
+ data =
+ "CONNECT www.example.com:443 HTTP/1.0\r\n" +
+ "Connection: keep-alive\r\n" +
+ "\r\n"
+
+ bytes = @parser << data
+
+ expect(bytes).to eq(64)
+ expect(data[bytes..-1]).to eq('')
+
+ expect(@headers).to eq({'Connection' => 'keep-alive'})
+ expect(@parser.upgrade_data).to eq('')
+ expect(@body).to be_empty
+ expect(@done).to be false
+ end
+
+ it "should reset to initial state" do
+ @parser << "GET / HTTP/1.0\r\n\r\n"
+
+ expect(@parser.http_method).to eq('GET')
+ expect(@parser.http_version).to eq([1,0])
+
+ expect(@parser.request_url).to eq('/')
+
+ expect(@parser.reset!).to be true
+
+ expect(@parser.http_version).to be_nil
+ expect(@parser.http_method).to be_nil
+ expect(@parser.status_code).to be_nil
+
+ expect(@parser.request_url).to be_nil
+ end
+
+ it "should optionally reset parser state on no-body responses" do
+ expect(@parser.reset!).to be true
+
+ @head, @complete = 0, 0
+ @parser.on_headers_complete = proc {|h| @head += 1; :reset }
+ @parser.on_message_complete = proc { @complete += 1 }
+ @parser.on_body = proc {|b| fail }
+
+ head_response = "HTTP/1.1 200 OK\r\nContent-Length:10\r\n\r\n"
+
+ @parser << head_response
+ expect(@head).to eq(1)
+ expect(@complete).to eq(1)
+
+ @parser << head_response
+ expect(@head).to eq(2)
+ expect(@complete).to eq(2)
+ end
+
+ it "should retain callbacks after reset" do
+ expect(@parser.reset!).to be true
+
+ @parser << "GET / HTTP/1.0\r\n\r\n"
+ expect(@started).to be true
+ expect(@headers).to eq({})
+ expect(@done).to be true
+ end
+
+ it "should parse headers incrementally" do
+ request =
+ "GET / HTTP/1.0\r\n" +
+ "Header1: value 1\r\n" +
+ "Header2: value 2\r\n" +
+ "\r\n"
+
+ while chunk = request.slice!(0,2) and !chunk.empty?
+ @parser << chunk
+ end
+
+ expect(@parser.headers).to eq({
+ 'Header1' => 'value 1',
+ 'Header2' => 'value 2'
+ })
+ end
+
+ it "should handle multiple headers using strings" do
+ @parser.header_value_type = :strings
+
+ @parser <<
+ "GET / HTTP/1.0\r\n" +
+ "Set-Cookie: PREF=ID=a7d2c98; expires=Fri, 05-Apr-2013 05:00:45 GMT; path=/; domain=.bob.com\r\n" +
+ "Set-Cookie: NID=46jSHxPM; path=/; domain=.bob.com; HttpOnly\r\n" +
+ "\r\n"
+
+ expect(@parser.headers["Set-Cookie"]).to eq("PREF=ID=a7d2c98; expires=Fri, 05-Apr-2013 05:00:45 GMT; path=/; domain=.bob.com, NID=46jSHxPM; path=/; domain=.bob.com; HttpOnly")
+ end
+
+ it "should handle multiple headers using strings" do
+ @parser.header_value_type = :arrays
+
+ @parser <<
+ "GET / HTTP/1.0\r\n" +
+ "Set-Cookie: PREF=ID=a7d2c98; expires=Fri, 05-Apr-2013 05:00:45 GMT; path=/; domain=.bob.com\r\n" +
+ "Set-Cookie: NID=46jSHxPM; path=/; domain=.bob.com; HttpOnly\r\n" +
+ "\r\n"
+
+ expect(@parser.headers["Set-Cookie"]).to eq([
+ "PREF=ID=a7d2c98; expires=Fri, 05-Apr-2013 05:00:45 GMT; path=/; domain=.bob.com",
+ "NID=46jSHxPM; path=/; domain=.bob.com; HttpOnly"
+ ])
+ end
+
+ it "should handle multiple headers using mixed" do
+ @parser.header_value_type = :mixed
+
+ @parser <<
+ "GET / HTTP/1.0\r\n" +
+ "Set-Cookie: PREF=ID=a7d2c98; expires=Fri, 05-Apr-2013 05:00:45 GMT; path=/; domain=.bob.com\r\n" +
+ "Set-Cookie: NID=46jSHxPM; path=/; domain=.bob.com; HttpOnly\r\n" +
+ "\r\n"
+
+ expect(@parser.headers["Set-Cookie"]).to eq([
+ "PREF=ID=a7d2c98; expires=Fri, 05-Apr-2013 05:00:45 GMT; path=/; domain=.bob.com",
+ "NID=46jSHxPM; path=/; domain=.bob.com; HttpOnly"
+ ])
+ end
+
+ it "should handle a single cookie using mixed" do
+ @parser.header_value_type = :mixed
+
+ @parser <<
+ "GET / HTTP/1.0\r\n" +
+ "Set-Cookie: PREF=ID=a7d2c98; expires=Fri, 05-Apr-2013 05:00:45 GMT; path=/; domain=.bob.com\r\n" +
+ "\r\n"
+
+ expect(@parser.headers["Set-Cookie"]).to eq("PREF=ID=a7d2c98; expires=Fri, 05-Apr-2013 05:00:45 GMT; path=/; domain=.bob.com")
+ end
+
+ it "should support alternative api" do
+ callbacks = double('callbacks')
+ allow(callbacks).to receive(:on_message_begin){ @started = true }
+ allow(callbacks).to receive(:on_headers_complete){ |e| @headers = e }
+ allow(callbacks).to receive(:on_body){ |chunk| @body << chunk }
+ allow(callbacks).to receive(:on_message_complete){ @done = true }
+
+ @parser = HTTP::Parser.new(callbacks)
+ @parser << "GET / HTTP/1.0\r\n\r\n"
+
+ expect(@started).to be true
+ expect(@headers).to eq({})
+ expect(@body).to eq('')
+ expect(@done).to be true
+ end
+
+ it "should ignore extra content beyond specified length" do
+ @parser <<
+ "GET / HTTP/1.0\r\n" +
+ "Content-Length: 5\r\n" +
+ "\r\n" +
+ "hello" +
+ " \n"
+
+ expect(@body).to eq('hello')
+ expect(@done).to be true
+ end
+
+ it 'sets upgrade_data if available' do
+ @parser <<
+ "GET /demo HTTP/1.1\r\n" +
+ "Connection: Upgrade\r\n" +
+ "Upgrade: WebSocket\r\n\r\n" +
+ "third key data"
+
+ expect(@parser.upgrade?).to be true
+ expect(@parser.upgrade_data).to eq('third key data')
+ end
+
+ it 'sets upgrade_data to blank if un-available' do
+ @parser <<
+ "GET /demo HTTP/1.1\r\n" +
+ "Connection: Upgrade\r\n" +
+ "Upgrade: WebSocket\r\n\r\n"
+
+ expect(@parser.upgrade?).to be true
+ expect(@parser.upgrade_data).to eq('')
+ end
+
+ it 'should stop parsing headers when instructed' do
+ request = "GET /websocket HTTP/1.1\r\n" +
+ "host: localhost\r\n" +
+ "connection: Upgrade\r\n" +
+ "upgrade: websocket\r\n" +
+ "sec-websocket-key: SD6/hpYbKjQ6Sown7pBbWQ==\r\n" +
+ "sec-websocket-version: 13\r\n" +
+ "\r\n"
+
+ @parser.on_headers_complete = proc { |e| :stop }
+ offset = (@parser << request)
+ expect(@parser.upgrade?).to be true
+ expect(@parser.upgrade_data).to eq('')
+ expect(offset).to eq(request.length)
+ end
+
+ it "should execute on_body on requests with no content-length" do
+ expect(@parser.reset!).to be true
+
+ @head, @complete, @body = 0, 0, 0
+ @parser.on_headers_complete = proc {|h| @head += 1 }
+ @parser.on_message_complete = proc { @complete += 1 }
+ @parser.on_body = proc {|b| @body += 1 }
+
+ head_response = "HTTP/1.1 200 OK\r\n\r\nstuff"
+
+ @parser << head_response
+ @parser << ''
+ expect(@head).to eq(1)
+ expect(@complete).to eq(1)
+ expect(@body).to eq(1)
+ end
+
+
+ %w[ request response ].each do |type|
+ JSON.parse(File.read(File.expand_path("../support/#{type}s.json", __FILE__))).each do |test|
+ test['headers'] ||= {}
+ next if !defined?(JRUBY_VERSION) and HTTP::Parser.strict? != test['strict']
+
+ it "should parse #{type}: #{test['name']}" do
+ @parser << test['raw']
+
+ expect(@parser.http_method).to eq(test['method'])
+ expect(@parser.keep_alive?).to eq(test['should_keep_alive'])
+
+ if test.has_key?('upgrade') and test['upgrade'] != 0
+ expect(@parser.upgrade?).to be true
+ expect(@parser.upgrade_data).to eq(test['upgrade'])
+ end
+
+ expect(@parser.send("http_major")).to eq(test["http_major"])
+ expect(@parser.send("http_minor")).to eq(test["http_minor"])
+
+ if test['type'] == 'HTTP_REQUEST'
+ if defined?(JRUBY_VERSION)
+ expect(@parser.send("request_url")).to eq(test["request_url"])
+ else
+ # It's created by rb_str_new(), so that encoding is Encoding::ASCII_8BIT a.k.a Encoding::BINARY
+ expect(@parser.send("request_url")).to eq(test["request_url"].force_encoding(Encoding::ASCII_8BIT))
+ end
+ else
+ expect(@parser.send("status_code")).to eq(test["status_code"])
+ expect(@parser.send("status")).to eq(test["status"].force_encoding(Encoding::ASCII_8BIT)) if !defined?(JRUBY_VERSION)
+ end
+
+ expect(@headers.size).to eq(test['num_headers'])
+ expect(@headers).to eq(test['headers'])
+
+ expect(@body).to eq(test['body'])
+ expect(@body.size).to eq(test['body_size']) if test['body_size']
+ end
+ end
+ end
+end
diff --git a/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/spec_helper.rb b/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/spec_helper.rb
new file mode 100644
index 0000000..a4295f9
--- /dev/null
+++ b/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/spec_helper.rb
@@ -0,0 +1 @@
+require "http_parser"
diff --git a/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/support/requests.json b/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/support/requests.json
new file mode 100644
index 0000000..4fefb01
--- /dev/null
+++ b/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/support/requests.json
@@ -0,0 +1,612 @@
+[
+ {
+ "name": "curl get",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /test HTTP/1.1\r\nUser-Agent: curl/7.18.0 (i486-pc-linux-gnu) libcurl/7.18.0 OpenSSL/0.9.8g zlib/1.2.3.3 libidn/1.1\r\nHost: 0.0.0.0=5000\r\nAccept: */*\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/test",
+ "request_url": "/test",
+ "num_headers": 3,
+ "headers": {
+ "User-Agent": "curl/7.18.0 (i486-pc-linux-gnu) libcurl/7.18.0 OpenSSL/0.9.8g zlib/1.2.3.3 libidn/1.1",
+ "Host": "0.0.0.0=5000",
+ "Accept": "*/*"
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "firefox get",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /favicon.ico HTTP/1.1\r\nHost: 0.0.0.0=5000\r\nUser-Agent: Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.9) Gecko/2008061015 Firefox/3.0\r\nAccept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8\r\nAccept-Language: en-us,en;q=0.5\r\nAccept-Encoding: gzip,deflate\r\nAccept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7\r\nKeep-Alive: 300\r\nConnection: keep-alive\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/favicon.ico",
+ "request_url": "/favicon.ico",
+ "num_headers": 8,
+ "headers": {
+ "Host": "0.0.0.0=5000",
+ "User-Agent": "Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.9) Gecko/2008061015 Firefox/3.0",
+ "Accept": "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8",
+ "Accept-Language": "en-us,en;q=0.5",
+ "Accept-Encoding": "gzip,deflate",
+ "Accept-Charset": "ISO-8859-1,utf-8;q=0.7,*;q=0.7",
+ "Keep-Alive": "300",
+ "Connection": "keep-alive"
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "dumbfuck",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /dumbfuck HTTP/1.1\r\naaaaaaaaaaaaa:++++++++++\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/dumbfuck",
+ "request_url": "/dumbfuck",
+ "num_headers": 1,
+ "headers": {
+ "aaaaaaaaaaaaa": "++++++++++"
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "fragment in url",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /forums/1/topics/2375?page=1#posts-17408 HTTP/1.1\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "page=1",
+ "fragment": "posts-17408",
+ "request_path": "/forums/1/topics/2375",
+ "request_url": "/forums/1/topics/2375?page=1#posts-17408",
+ "num_headers": 0,
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "get no headers no body",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /get_no_headers_no_body/world HTTP/1.1\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/get_no_headers_no_body/world",
+ "request_url": "/get_no_headers_no_body/world",
+ "num_headers": 0,
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "get one header no body",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /get_one_header_no_body HTTP/1.1\r\nAccept: */*\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/get_one_header_no_body",
+ "request_url": "/get_one_header_no_body",
+ "num_headers": 1,
+ "headers": {
+ "Accept": "*/*"
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "get funky content length body hello",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /get_funky_content_length_body_hello HTTP/1.0\r\nconTENT-Length: 5\r\n\r\nHELLO",
+ "should_keep_alive": false,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 0,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/get_funky_content_length_body_hello",
+ "request_url": "/get_funky_content_length_body_hello",
+ "num_headers": 1,
+ "headers": {
+ "conTENT-Length": "5"
+ },
+ "body": "HELLO",
+ "strict": true
+ },
+ {
+ "name": "post identity body world",
+ "type": "HTTP_REQUEST",
+ "raw": "POST /post_identity_body_world?q=search#hey HTTP/1.1\r\nAccept: */*\r\nTransfer-Encoding: identity\r\nContent-Length: 5\r\n\r\nWorld",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "POST",
+ "query_string": "q=search",
+ "fragment": "hey",
+ "request_path": "/post_identity_body_world",
+ "request_url": "/post_identity_body_world?q=search#hey",
+ "num_headers": 3,
+ "headers": {
+ "Accept": "*/*",
+ "Transfer-Encoding": "identity",
+ "Content-Length": "5"
+ },
+ "body": "World",
+ "strict": true
+ },
+ {
+ "name": "post - chunked body: all your base are belong to us",
+ "type": "HTTP_REQUEST",
+ "raw": "POST /post_chunked_all_your_base HTTP/1.1\r\nTransfer-Encoding: chunked\r\n\r\n1e\r\nall your base are belong to us\r\n0\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "POST",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/post_chunked_all_your_base",
+ "request_url": "/post_chunked_all_your_base",
+ "num_headers": 1,
+ "headers": {
+ "Transfer-Encoding": "chunked"
+ },
+ "body": "all your base are belong to us",
+ "strict": true
+ },
+ {
+ "name": "two chunks ; triple zero ending",
+ "type": "HTTP_REQUEST",
+ "raw": "POST /two_chunks_mult_zero_end HTTP/1.1\r\nTransfer-Encoding: chunked\r\n\r\n5\r\nhello\r\n6\r\n world\r\n000\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "POST",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/two_chunks_mult_zero_end",
+ "request_url": "/two_chunks_mult_zero_end",
+ "num_headers": 1,
+ "headers": {
+ "Transfer-Encoding": "chunked"
+ },
+ "body": "hello world",
+ "strict": true
+ },
+ {
+ "name": "chunked with trailing headers. blech.",
+ "type": "HTTP_REQUEST",
+ "raw": "POST /chunked_w_trailing_headers HTTP/1.1\r\nTransfer-Encoding: chunked\r\n\r\n5\r\nhello\r\n6\r\n world\r\n0\r\nVary: *\r\nContent-Type: text/plain\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "POST",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/chunked_w_trailing_headers",
+ "request_url": "/chunked_w_trailing_headers",
+ "num_headers": 3,
+ "headers": {
+ "Transfer-Encoding": "chunked",
+ "Vary": "*",
+ "Content-Type": "text/plain"
+ },
+ "body": "hello world",
+ "strict": true
+ },
+ {
+ "name": "with bullshit after the length",
+ "type": "HTTP_REQUEST",
+ "raw": "POST /chunked_w_bullshit_after_length HTTP/1.1\r\nTransfer-Encoding: chunked\r\n\r\n5; ihatew3;whatthefuck=aretheseparametersfor\r\nhello\r\n6; blahblah; blah\r\n world\r\n0\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "POST",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/chunked_w_bullshit_after_length",
+ "request_url": "/chunked_w_bullshit_after_length",
+ "num_headers": 1,
+ "headers": {
+ "Transfer-Encoding": "chunked"
+ },
+ "body": "hello world",
+ "strict": true
+ },
+ {
+ "name": "with quotes",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /with_\"stupid\"_quotes?foo=\"bar\" HTTP/1.1\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "foo=\"bar\"",
+ "fragment": "",
+ "request_path": "/with_\"stupid\"_quotes",
+ "request_url": "/with_\"stupid\"_quotes?foo=\"bar\"",
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "apachebench get",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /test HTTP/1.0\r\nHost: 0.0.0.0:5000\r\nUser-Agent: ApacheBench/2.3\r\nAccept: */*\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 0,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/test",
+ "request_url": "/test",
+ "num_headers": 3,
+ "headers": {
+ "Host": "0.0.0.0:5000",
+ "User-Agent": "ApacheBench/2.3",
+ "Accept": "*/*"
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "query url with question mark",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /test.cgi?foo=bar?baz HTTP/1.1\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "foo=bar?baz",
+ "fragment": "",
+ "request_path": "/test.cgi",
+ "request_url": "/test.cgi?foo=bar?baz",
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "newline prefix get",
+ "type": "HTTP_REQUEST",
+ "raw": "\r\nGET /test HTTP/1.1\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/test",
+ "request_url": "/test",
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "upgrade request",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /demo HTTP/1.1\r\nHost: example.com\r\nConnection: Upgrade\r\nSec-WebSocket-Key2: 12998 5 Y3 1 .P00\r\nSec-WebSocket-Protocol: sample\r\nUpgrade: WebSocket\r\nSec-WebSocket-Key1: 4 @1 46546xW%0l 1 5\r\nOrigin: http://example.com\r\n\r\nHot diggity dogg",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/demo",
+ "request_url": "/demo",
+ "num_headers": 7,
+ "upgrade": "Hot diggity dogg",
+ "headers": {
+ "Host": "example.com",
+ "Connection": "Upgrade",
+ "Sec-WebSocket-Key2": "12998 5 Y3 1 .P00",
+ "Sec-WebSocket-Protocol": "sample",
+ "Upgrade": "WebSocket",
+ "Sec-WebSocket-Key1": "4 @1 46546xW%0l 1 5",
+ "Origin": "http://example.com"
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "connect request",
+ "type": "HTTP_REQUEST",
+ "raw": "CONNECT 0-home0.netscape.com:443 HTTP/1.0\r\nUser-agent: Mozilla/1.1N\r\nProxy-authorization: basic aGVsbG86d29ybGQ=\r\n\r\nsome data\r\nand yet even more data",
+ "should_keep_alive": false,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 0,
+ "method": "CONNECT",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "",
+ "request_url": "0-home0.netscape.com:443",
+ "num_headers": 2,
+ "upgrade": "some data\r\nand yet even more data",
+ "headers": {
+ "User-agent": "Mozilla/1.1N",
+ "Proxy-authorization": "basic aGVsbG86d29ybGQ="
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "report request",
+ "type": "HTTP_REQUEST",
+ "raw": "REPORT /test HTTP/1.1\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "REPORT",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/test",
+ "request_url": "/test",
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "request with no http version",
+ "type": "HTTP_REQUEST",
+ "raw": "GET /\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": false,
+ "http_major": 0,
+ "http_minor": 9,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/",
+ "request_url": "/",
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "m-search request",
+ "type": "HTTP_REQUEST",
+ "raw": "M-SEARCH * HTTP/1.1\r\nHOST: 239.255.255.250:1900\r\nMAN: \"ssdp:discover\"\r\nST: \"ssdp:all\"\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "M-SEARCH",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "*",
+ "request_url": "*",
+ "num_headers": 3,
+ "headers": {
+ "HOST": "239.255.255.250:1900",
+ "MAN": "\"ssdp:discover\"",
+ "ST": "\"ssdp:all\""
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "line folding in header value",
+ "type": "HTTP_REQUEST",
+ "raw": "GET / HTTP/1.1\r\nLine1: abc\r\n\tdef\r\n ghi\r\n\t\tjkl\r\n mno \r\n\t \tqrs\r\nLine2: \t line2\t\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/",
+ "request_url": "/",
+ "num_headers": 2,
+ "headers": {
+ "Line1": "abc\tdef ghi\t\tjkl mno \t \tqrs",
+ "Line2": "line2\t"
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "host terminated by a query string",
+ "type": "HTTP_REQUEST",
+ "raw": "GET http://hypnotoad.org?hail=all HTTP/1.1\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "hail=all",
+ "fragment": "",
+ "request_path": "",
+ "request_url": "http://hypnotoad.org?hail=all",
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "host:port terminated by a query string",
+ "type": "HTTP_REQUEST",
+ "raw": "GET http://hypnotoad.org:1234?hail=all HTTP/1.1\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "hail=all",
+ "fragment": "",
+ "request_path": "",
+ "request_url": "http://hypnotoad.org:1234?hail=all",
+ "port": 1234,
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "host:port terminated by a space",
+ "type": "HTTP_REQUEST",
+ "raw": "GET http://hypnotoad.org:1234 HTTP/1.1\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "",
+ "request_url": "http://hypnotoad.org:1234",
+ "port": 1234,
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "PATCH request",
+ "type": "HTTP_REQUEST",
+ "raw": "PATCH /file.txt HTTP/1.1\r\nHost: www.example.com\r\nContent-Type: application/example\r\nIf-Match: \"e0023aa4e\"\r\nContent-Length: 10\r\n\r\ncccccccccc",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "PATCH",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "/file.txt",
+ "request_url": "/file.txt",
+ "num_headers": 4,
+ "headers": {
+ "Host": "www.example.com",
+ "Content-Type": "application/example",
+ "If-Match": "\"e0023aa4e\"",
+ "Content-Length": "10"
+ },
+ "body": "cccccccccc",
+ "strict": true
+ },
+ {
+ "name": "connect caps request",
+ "type": "HTTP_REQUEST",
+ "raw": "CONNECT HOME0.NETSCAPE.COM:443 HTTP/1.0\r\nUser-agent: Mozilla/1.1N\r\nProxy-authorization: basic aGVsbG86d29ybGQ=\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 0,
+ "method": "CONNECT",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "",
+ "request_url": "HOME0.NETSCAPE.COM:443",
+ "num_headers": 2,
+ "upgrade": "",
+ "headers": {
+ "User-agent": "Mozilla/1.1N",
+ "Proxy-authorization": "basic aGVsbG86d29ybGQ="
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "utf-8 path request",
+ "type": "HTTP_REQUEST",
+ "strict": false,
+ "raw": "GET /δ¶/δt/pope?q=1#narf HTTP/1.1\r\nHost: github.com\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "method": "GET",
+ "query_string": "q=1",
+ "fragment": "narf",
+ "request_path": "/δ¶/δt/pope",
+ "request_url": "/δ¶/δt/pope?q=1#narf",
+ "num_headers": 1,
+ "headers": {
+ "Host": "github.com"
+ },
+ "body": ""
+ },
+ {
+ "name": "hostname underscore",
+ "type": "HTTP_REQUEST",
+ "strict": false,
+ "raw": "CONNECT home_0.netscape.com:443 HTTP/1.0\r\nUser-agent: Mozilla/1.1N\r\nProxy-authorization: basic aGVsbG86d29ybGQ=\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 0,
+ "method": "CONNECT",
+ "query_string": "",
+ "fragment": "",
+ "request_path": "",
+ "request_url": "home_0.netscape.com:443",
+ "num_headers": 2,
+ "upgrade": "",
+ "headers": {
+ "User-agent": "Mozilla/1.1N",
+ "Proxy-authorization": "basic aGVsbG86d29ybGQ="
+ },
+ "body": ""
+ }
+] \ No newline at end of file
diff --git a/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/support/responses.json b/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/support/responses.json
new file mode 100644
index 0000000..a033f3b
--- /dev/null
+++ b/vendor/bundle/ruby/3.4.0/gems/http_parser.rb-0.8.0/spec/support/responses.json
@@ -0,0 +1,395 @@
+[
+ {
+ "name": "google 301",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 301 Moved Permanently\r\nLocation: http://www.google.com/\r\nContent-Type: text/html; charset=UTF-8\r\nDate: Sun, 26 Apr 2009 11:11:49 GMT\r\nExpires: Tue, 26 May 2009 11:11:49 GMT\r\nX-$PrototypeBI-Version: 1.6.0.3\r\nCache-Control: public, max-age=2592000\r\nServer: gws\r\nContent-Length: 219 \r\n\r\n<HTML><HEAD><meta http-equiv=\"content-type\" content=\"text/html;charset=utf-8\">\n<TITLE>301 Moved</TITLE></HEAD><BODY>\n<H1>301 Moved</H1>\nThe document has moved\n<A HREF=\"http://www.google.com/\">here</A>.\r\n</BODY></HTML>\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 301,
+ "status": "Moved Permanently",
+ "num_headers": 8,
+ "headers": {
+ "Location": "http://www.google.com/",
+ "Content-Type": "text/html; charset=UTF-8",
+ "Date": "Sun, 26 Apr 2009 11:11:49 GMT",
+ "Expires": "Tue, 26 May 2009 11:11:49 GMT",
+ "X-$PrototypeBI-Version": "1.6.0.3",
+ "Cache-Control": "public, max-age=2592000",
+ "Server": "gws",
+ "Content-Length": "219 "
+ },
+ "body": "<HTML><HEAD><meta http-equiv=\"content-type\" content=\"text/html;charset=utf-8\">\n<TITLE>301 Moved</TITLE></HEAD><BODY>\n<H1>301 Moved</H1>\nThe document has moved\n<A HREF=\"http://www.google.com/\">here</A>.\r\n</BODY></HTML>\r\n",
+ "strict": true
+ },
+ {
+ "name": "no content-length response",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 200 OK\r\nDate: Tue, 04 Aug 2009 07:59:32 GMT\r\nServer: Apache\r\nX-Powered-By: Servlet/2.5 JSP/2.1\r\nContent-Type: text/xml; charset=utf-8\r\nConnection: close\r\n\r\n<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<SOAP-ENV:Envelope xmlns:SOAP-ENV=\"http://schemas.xmlsoap.org/soap/envelope/\">\n <SOAP-ENV:Body>\n <SOAP-ENV:Fault>\n <faultcode>SOAP-ENV:Client</faultcode>\n <faultstring>Client Error</faultstring>\n </SOAP-ENV:Fault>\n </SOAP-ENV:Body>\n</SOAP-ENV:Envelope>",
+ "should_keep_alive": false,
+ "message_complete_on_eof": true,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 5,
+ "headers": {
+ "Date": "Tue, 04 Aug 2009 07:59:32 GMT",
+ "Server": "Apache",
+ "X-Powered-By": "Servlet/2.5 JSP/2.1",
+ "Content-Type": "text/xml; charset=utf-8",
+ "Connection": "close"
+ },
+ "body": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<SOAP-ENV:Envelope xmlns:SOAP-ENV=\"http://schemas.xmlsoap.org/soap/envelope/\">\n <SOAP-ENV:Body>\n <SOAP-ENV:Fault>\n <faultcode>SOAP-ENV:Client</faultcode>\n <faultstring>Client Error</faultstring>\n </SOAP-ENV:Fault>\n </SOAP-ENV:Body>\n</SOAP-ENV:Envelope>",
+ "strict": true
+ },
+ {
+ "name": "404 no headers no body",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 404 Not Found\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": true,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 404,
+ "status": "Not Found",
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body_size": 0,
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "301 no response phrase",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 301\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": true,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 301,
+ "status": "",
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "200 trailing space on chunked body",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 200 OK\r\nContent-Type: text/plain\r\nTransfer-Encoding: chunked\r\n\r\n25 \r\nThis is the data in the first chunk\r\n\r\n1C\r\nand this is the second one\r\n\r\n0 \r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 2,
+ "headers": {
+ "Content-Type": "text/plain",
+ "Transfer-Encoding": "chunked"
+ },
+ "body_size": 65,
+ "body": "This is the data in the first chunk\r\nand this is the second one\r\n",
+ "strict": true
+ },
+ {
+ "name": "no carriage ret",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 200 OK\nContent-Type: text/html; charset=utf-8\nConnection: close\n\nthese headers are from http://news.ycombinator.com/",
+ "should_keep_alive": false,
+ "message_complete_on_eof": true,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 2,
+ "headers": {
+ "Content-Type": "text/html; charset=utf-8",
+ "Connection": "close"
+ },
+ "body": "these headers are from http://news.ycombinator.com/",
+ "strict": true
+ },
+ {
+ "name": "proxy connection",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 200 OK\r\nContent-Type: text/html; charset=UTF-8\r\nContent-Length: 11\r\nProxy-Connection: close\r\nDate: Thu, 31 Dec 2009 20:55:48 +0000\r\n\r\nhello world",
+ "should_keep_alive": false,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 4,
+ "headers": {
+ "Content-Type": "text/html; charset=UTF-8",
+ "Content-Length": "11",
+ "Proxy-Connection": "close",
+ "Date": "Thu, 31 Dec 2009 20:55:48 +0000"
+ },
+ "body": "hello world",
+ "strict": true
+ },
+ {
+ "name": "underscore header key",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 200 OK\r\nServer: DCLK-AdSvr\r\nContent-Type: text/xml\r\nContent-Length: 0\r\nDCLK_imp: v7;x;114750856;0-0;0;17820020;0/0;21603567/21621457/1;;~okv=;dcmt=text/xml;;~cs=o\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 4,
+ "headers": {
+ "Server": "DCLK-AdSvr",
+ "Content-Type": "text/xml",
+ "Content-Length": "0",
+ "DCLK_imp": "v7;x;114750856;0-0;0;17820020;0/0;21603567/21621457/1;;~okv=;dcmt=text/xml;;~cs=o"
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "bonjourmadame.fr",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.0 301 Moved Permanently\r\nDate: Thu, 03 Jun 2010 09:56:32 GMT\r\nServer: Apache/2.2.3 (Red Hat)\r\nCache-Control: public\r\nPragma: \r\nLocation: http://www.bonjourmadame.fr/\r\nVary: Accept-Encoding\r\nContent-Length: 0\r\nContent-Type: text/html; charset=UTF-8\r\nConnection: keep-alive\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 0,
+ "status_code": 301,
+ "status": "Moved Permanently",
+ "num_headers": 9,
+ "headers": {
+ "Date": "Thu, 03 Jun 2010 09:56:32 GMT",
+ "Server": "Apache/2.2.3 (Red Hat)",
+ "Cache-Control": "public",
+ "Pragma": "",
+ "Location": "http://www.bonjourmadame.fr/",
+ "Vary": "Accept-Encoding",
+ "Content-Length": "0",
+ "Content-Type": "text/html; charset=UTF-8",
+ "Connection": "keep-alive"
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "field underscore",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 200 OK\r\nDate: Tue, 28 Sep 2010 01:14:13 GMT\r\nServer: Apache\r\nCache-Control: no-cache, must-revalidate\r\nExpires: Mon, 26 Jul 1997 05:00:00 GMT\r\n.et-Cookie: PlaxoCS=1274804622353690521; path=/; domain=.plaxo.com\r\nVary: Accept-Encoding\r\n_eep-Alive: timeout=45\r\n_onnection: Keep-Alive\r\nTransfer-Encoding: chunked\r\nContent-Type: text/html\r\nConnection: close\r\n\r\n0\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 11,
+ "headers": {
+ "Date": "Tue, 28 Sep 2010 01:14:13 GMT",
+ "Server": "Apache",
+ "Cache-Control": "no-cache, must-revalidate",
+ "Expires": "Mon, 26 Jul 1997 05:00:00 GMT",
+ ".et-Cookie": "PlaxoCS=1274804622353690521; path=/; domain=.plaxo.com",
+ "Vary": "Accept-Encoding",
+ "_eep-Alive": "timeout=45",
+ "_onnection": "Keep-Alive",
+ "Transfer-Encoding": "chunked",
+ "Content-Type": "text/html",
+ "Connection": "close"
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "non-ASCII in status line",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 500 Oriëntatieprobleem\r\nDate: Fri, 5 Nov 2010 23:07:12 GMT+2\r\nContent-Length: 0\r\nConnection: close\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 500,
+ "status": "Oriëntatieprobleem",
+ "num_headers": 3,
+ "headers": {
+ "Date": "Fri, 5 Nov 2010 23:07:12 GMT+2",
+ "Content-Length": "0",
+ "Connection": "close"
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "http version 0.9",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/0.9 200 OK\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": true,
+ "http_major": 0,
+ "http_minor": 9,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "neither content-length nor transfer-encoding response",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 200 OK\r\nContent-Type: text/plain\r\n\r\nhello world",
+ "should_keep_alive": false,
+ "message_complete_on_eof": true,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 1,
+ "headers": {
+ "Content-Type": "text/plain"
+ },
+ "body": "hello world",
+ "strict": true
+ },
+ {
+ "name": "HTTP/1.0 with keep-alive and EOF-terminated 200 status",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.0 200 OK\r\nConnection: keep-alive\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": true,
+ "http_major": 1,
+ "http_minor": 0,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 1,
+ "headers": {
+ "Connection": "keep-alive"
+ },
+ "body_size": 0,
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "HTTP/1.0 with keep-alive and a 204 status",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.0 204 No content\r\nConnection: keep-alive\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 0,
+ "status_code": 204,
+ "status": "No content",
+ "num_headers": 1,
+ "headers": {
+ "Connection": "keep-alive"
+ },
+ "body_size": 0,
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "HTTP/1.1 with an EOF-terminated 200 status",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 200 OK\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": true,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body_size": 0,
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "HTTP/1.1 with a 204 status",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 204 No content\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 204,
+ "status": "No content",
+ "num_headers": 0,
+ "headers": {
+
+ },
+ "body_size": 0,
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "HTTP/1.1 with a 204 status and keep-alive disabled",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 204 No content\r\nConnection: close\r\n\r\n",
+ "should_keep_alive": false,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 204,
+ "status": "No content",
+ "num_headers": 1,
+ "headers": {
+ "Connection": "close"
+ },
+ "body_size": 0,
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "HTTP/1.1 with chunked endocing and a 200 response",
+ "type": "HTTP_RESPONSE",
+ "raw": "HTTP/1.1 200 OK\r\nTransfer-Encoding: chunked\r\n\r\n0\r\n\r\n",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 1,
+ "headers": {
+ "Transfer-Encoding": "chunked"
+ },
+ "body_size": 0,
+ "body": "",
+ "strict": true
+ },
+ {
+ "name": "field space",
+ "type": "HTTP_RESPONSE",
+ "strict": false,
+ "raw": "HTTP/1.1 200 OK\r\nServer: Microsoft-IIS/6.0\r\nX-Powered-By: ASP.NET\r\nen-US Content-Type: text/xml\r\nContent-Type: text/xml\r\nContent-Length: 16\r\nDate: Fri, 23 Jul 2010 18:45:38 GMT\r\nConnection: keep-alive\r\n\r\n<xml>hello</xml>",
+ "should_keep_alive": true,
+ "message_complete_on_eof": false,
+ "http_major": 1,
+ "http_minor": 1,
+ "status_code": 200,
+ "status": "OK",
+ "num_headers": 7,
+ "headers": {
+ "Server": "Microsoft-IIS/6.0",
+ "X-Powered-By": "ASP.NET",
+ "en-US Content-Type": "text/xml",
+ "Content-Type": "text/xml",
+ "Content-Length": "16",
+ "Date": "Fri, 23 Jul 2010 18:45:38 GMT",
+ "Connection": "keep-alive"
+ },
+ "body": "<xml>hello</xml>"
+ }
+] \ No newline at end of file