зеркало из https://github.com/github/ruby.git
[ruby/net-http] Add ignore_eof access to HTTP and HTTPResponse
The ignore_eof setting on HTTPResponse makes it so an EOFError is raised when reading bodies with a defined Content-Length, if the body read was truncated due to the socket be closed. The ignore_eof setting on HTTP sets the values used in responses that are created by the object. For backwards compatibility, the default is for both settings is true. However, unless you are specifically tested for and handling truncated responses, it's a good idea to set ignore_eof to false so that errors are raised for truncated responses, instead of those errors silently being ignored. Fixes [Bug #14972] https://github.com/ruby/net-http/commit/4d47e34995
This commit is contained in:
Родитель
fada4d24f9
Коммит
90ccc5674a
|
@ -699,6 +699,7 @@ module Net #:nodoc:
|
||||||
@max_retries = 1
|
@max_retries = 1
|
||||||
@debug_output = nil
|
@debug_output = nil
|
||||||
@response_body_encoding = false
|
@response_body_encoding = false
|
||||||
|
@ignore_eof = true
|
||||||
|
|
||||||
@proxy_from_env = false
|
@proxy_from_env = false
|
||||||
@proxy_uri = nil
|
@proxy_uri = nil
|
||||||
|
@ -839,6 +840,10 @@ module Net #:nodoc:
|
||||||
# The default value is 2 seconds.
|
# The default value is 2 seconds.
|
||||||
attr_accessor :keep_alive_timeout
|
attr_accessor :keep_alive_timeout
|
||||||
|
|
||||||
|
# Whether to ignore EOF when reading response bodies with defined
|
||||||
|
# Content-Length headers. For backwards compatibility, the default is true.
|
||||||
|
attr_accessor :ignore_eof
|
||||||
|
|
||||||
# Returns true if the HTTP session has been started.
|
# Returns true if the HTTP session has been started.
|
||||||
def started?
|
def started?
|
||||||
@started
|
@started
|
||||||
|
@ -1606,6 +1611,7 @@ module Net #:nodoc:
|
||||||
res = HTTPResponse.read_new(@socket)
|
res = HTTPResponse.read_new(@socket)
|
||||||
res.decode_content = req.decode_content
|
res.decode_content = req.decode_content
|
||||||
res.body_encoding = @response_body_encoding
|
res.body_encoding = @response_body_encoding
|
||||||
|
res.ignore_eof = @ignore_eof
|
||||||
end while res.kind_of?(HTTPInformation)
|
end while res.kind_of?(HTTPInformation)
|
||||||
|
|
||||||
res.uri = req.uri
|
res.uri = req.uri
|
||||||
|
|
|
@ -85,6 +85,7 @@ class Net::HTTPResponse
|
||||||
@uri = nil
|
@uri = nil
|
||||||
@decode_content = false
|
@decode_content = false
|
||||||
@body_encoding = false
|
@body_encoding = false
|
||||||
|
@ignore_eof = true
|
||||||
end
|
end
|
||||||
|
|
||||||
# The HTTP version supported by the server.
|
# The HTTP version supported by the server.
|
||||||
|
@ -119,6 +120,10 @@ class Net::HTTPResponse
|
||||||
@body_encoding = value
|
@body_encoding = value
|
||||||
end
|
end
|
||||||
|
|
||||||
|
# Whether to ignore EOF when reading bodies with a specified Content-Length
|
||||||
|
# header.
|
||||||
|
attr_accessor :ignore_eof
|
||||||
|
|
||||||
def inspect
|
def inspect
|
||||||
"#<#{self.class} #{@code} #{@message} readbody=#{@read}>"
|
"#<#{self.class} #{@code} #{@message} readbody=#{@read}>"
|
||||||
end
|
end
|
||||||
|
@ -459,7 +464,7 @@ class Net::HTTPResponse
|
||||||
|
|
||||||
clen = content_length()
|
clen = content_length()
|
||||||
if clen
|
if clen
|
||||||
@socket.read clen, dest, true # ignore EOF
|
@socket.read clen, dest, @ignore_eof
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
clen = range_length()
|
clen = range_length()
|
||||||
|
|
|
@ -1348,3 +1348,33 @@ class TestNetHTTPForceEncoding < Test::Unit::TestCase
|
||||||
assert_equal(Encoding::UTF_8, res.body.encoding)
|
assert_equal(Encoding::UTF_8, res.body.encoding)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
class TestNetHTTPPartialResponse < Test::Unit::TestCase
|
||||||
|
CONFIG = {
|
||||||
|
'host' => '127.0.0.1',
|
||||||
|
'proxy_host' => nil,
|
||||||
|
'proxy_port' => nil,
|
||||||
|
}
|
||||||
|
|
||||||
|
include TestNetHTTPUtils
|
||||||
|
|
||||||
|
def test_partial_response
|
||||||
|
str = "0123456789"
|
||||||
|
@server.mount_proc('/') do |req, res|
|
||||||
|
res.status = 200
|
||||||
|
res['Content-Type'] = 'text/plain'
|
||||||
|
|
||||||
|
res.body = str
|
||||||
|
res['Content-Length'] = str.length + 1
|
||||||
|
end
|
||||||
|
@server.mount_proc('/show_ip') { |req, res| res.body = req.remote_ip }
|
||||||
|
|
||||||
|
http = Net::HTTP.new(config('host'), config('port'))
|
||||||
|
res = http.get('/')
|
||||||
|
assert_equal(str, res.body)
|
||||||
|
|
||||||
|
http = Net::HTTP.new(config('host'), config('port'))
|
||||||
|
http.ignore_eof = false
|
||||||
|
assert_raise(EOFError) {http.get('/')}
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
Загрузка…
Ссылка в новой задаче