Skip to content

Commit

Permalink
Fix parser so it properly parses headers
Browse files Browse the repository at this point in the history
..when they are returned in parts

Resolves: #589
  • Loading branch information
Piotr Boniecki committed Jan 22, 2020
1 parent edfa4f1 commit e623d67
Show file tree
Hide file tree
Showing 2 changed files with 65 additions and 6 deletions.
26 changes: 20 additions & 6 deletions lib/http/response/parser.rb
Expand Up @@ -49,14 +49,17 @@ def status_code
#

def on_header_field(_response, field)
@field = field
append_header if @reading_header_value
@field << field
end

def on_header_value(_response, value)
@headers.add(@field, value) if @field
@reading_header_value = true
@field_value << value
end

def on_headers_complete(_reposse)
append_header if @reading_header_value
@finished[:headers] = true
end

Expand Down Expand Up @@ -89,15 +92,26 @@ def on_message_complete(_response)
def reset
@state.reset!

@finished = Hash.new(false)
@headers = HTTP::Headers.new
@field = nil
@chunk = nil
@finished = Hash.new(false)
@headers = HTTP::Headers.new
@reading_header_value = false
@field = +""
@field_value = +""
@chunk = nil
end

def finished?
@finished[:message]
end

private

def append_header
@headers.add(@field, @field_value)
@reading_header_value = false
@field_value = +""
@field = +""
end
end
end
end
45 changes: 45 additions & 0 deletions spec/lib/http/response/parser_spec.rb
@@ -0,0 +1,45 @@
# frozen_string_literal: true

RSpec.describe HTTP::Response::Parser do
subject(:parser) { described_class.new }
let(:raw_response) do
"HTTP/1.1 200 OK\r\nContent-Length: 2\r\nContent-Type: application/json\r\nMyHeader: val\r\nEmptyHeader: \r\n\r\n{}"
end
let(:expected_headers) do
{
"Content-Length" => "2",
"Content-Type" => "application/json",
"MyHeader" => "val",
"EmptyHeader" => ""
}
end
let(:expected_body) { "{}" }

before do
parts.each { |part| subject.add(part) }
end

context "whole response in one part" do
let(:parts) { [raw_response] }

it "parses headers" do
expect(subject.headers.to_h).to eq(expected_headers)
end

it "parses body" do
expect(subject.read(expected_body.size)).to eq(expected_body)
end
end

context "response in many parts" do
let(:parts) { raw_response.split(//) }

it "parses headers" do
expect(subject.headers.to_h).to eq(expected_headers)
end

it "parses body" do
expect(subject.read(expected_body.size)).to eq(expected_body)
end
end
end

0 comments on commit e623d67

Please sign in to comment.