httpclient 2.6.0.1 → 2.8.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.md +1 -1
- data/bin/httpclient +7 -1
- data/lib/http-access2.rb +1 -1
- data/lib/httpclient/auth.rb +3 -3
- data/lib/httpclient/cacert.pem +3952 -0
- data/lib/httpclient/connection.rb +1 -1
- data/lib/httpclient/cookie.rb +10 -10
- data/lib/httpclient/http.rb +9 -4
- data/lib/httpclient/jruby_ssl_socket.rb +588 -0
- data/lib/httpclient/session.rb +199 -262
- data/lib/httpclient/ssl_config.rb +123 -114
- data/lib/httpclient/ssl_socket.rb +150 -0
- data/lib/httpclient/timeout.rb +1 -1
- data/lib/httpclient/util.rb +33 -1
- data/lib/httpclient/version.rb +1 -1
- data/lib/httpclient/webagent-cookie.rb +2 -2
- data/lib/httpclient.rb +72 -20
- data/lib/oauthclient.rb +2 -1
- data/test/helper.rb +7 -5
- data/test/jruby_ssl_socket/test_pemutils.rb +32 -0
- data/test/test_auth.rb +28 -9
- data/test/test_cookie.rb +2 -2
- data/test/test_http-access2.rb +2 -0
- data/test/test_httpclient.rb +143 -23
- data/test/test_ssl.rb +295 -17
- data/test/test_webagent-cookie.rb +2 -2
- metadata +14 -10
- /data/lib/httpclient/{cacert.p7s → cacert1024.pem} +0 -0
- /data/test/{ca-chain.cert → ca-chain.pem} +0 -0
data/lib/httpclient.rb
CHANGED
@@ -1,5 +1,5 @@
|
|
1
1
|
# HTTPClient - HTTP client library.
|
2
|
-
# Copyright (C) 2000-
|
2
|
+
# Copyright (C) 2000-2015 NAKAMURA, Hiroshi <nahi@ruby-lang.org>.
|
3
3
|
#
|
4
4
|
# This program is copyrighted free software by NAKAMURA, Hiroshi. You can
|
5
5
|
# redistribute it and/or modify it under the same terms of Ruby's license;
|
@@ -149,6 +149,16 @@ require 'httpclient/cookie'
|
|
149
149
|
# clnt.ssl_config.set_client_cert_file(user_cert_file, user_key_file)
|
150
150
|
# clnt.get(https_url)
|
151
151
|
#
|
152
|
+
# 4. Revocation check. On JRuby you can set following options to let
|
153
|
+
# HTTPClient to perform revocation check with CRL and OCSP:
|
154
|
+
#
|
155
|
+
# -J-Dcom.sun.security.enableCRLDP=true -J-Dcom.sun.net.ssl.checkRevocation=true
|
156
|
+
# ex. jruby -J-Dcom.sun.security.enableCRLDP=true -J-Dcom.sun.net.ssl.checkRevocation=true app.rb
|
157
|
+
# Revoked cert example: https://test-sspev.verisign.com:2443/test-SSPEV-revoked-verisign.html
|
158
|
+
#
|
159
|
+
# On other platform you can download CRL by yourself and set it via
|
160
|
+
# SSLConfig#add_crl.
|
161
|
+
#
|
152
162
|
# === Handling Cookies
|
153
163
|
#
|
154
164
|
# 1. Using volatile Cookies. Nothing to do. HTTPClient handles Cookies.
|
@@ -299,7 +309,6 @@ class HTTPClient
|
|
299
309
|
if assignable
|
300
310
|
aname = name + '='
|
301
311
|
define_method(aname) { |rhs|
|
302
|
-
reset_all
|
303
312
|
@session_manager.__send__(aname, rhs)
|
304
313
|
}
|
305
314
|
end
|
@@ -326,7 +335,7 @@ class HTTPClient
|
|
326
335
|
attr_accessor :follow_redirect_count
|
327
336
|
# Base url of resources.
|
328
337
|
attr_accessor :base_url
|
329
|
-
#
|
338
|
+
# Default request header.
|
330
339
|
attr_accessor :default_header
|
331
340
|
|
332
341
|
# Set HTTP version as a String:: 'HTTP/1.0' or 'HTTP/1.1'
|
@@ -346,6 +355,8 @@ class HTTPClient
|
|
346
355
|
# if your ruby is older than 2005-09-06, do not set socket_sync = false to
|
347
356
|
# avoid an SSL socket blocking bug in openssl/buffering.rb.
|
348
357
|
attr_proxy(:socket_sync, true)
|
358
|
+
# Enables TCP keepalive; no timing settings exist at present
|
359
|
+
attr_proxy(:tcp_keepalive, true)
|
349
360
|
# User-Agent header in HTTP request.
|
350
361
|
attr_proxy(:agent_name, true)
|
351
362
|
# From header in HTTP request.
|
@@ -355,6 +366,9 @@ class HTTPClient
|
|
355
366
|
attr_proxy(:test_loopback_http_response)
|
356
367
|
# Decompress a compressed (with gzip or deflate) content body transparently. false by default.
|
357
368
|
attr_proxy(:transparent_gzip_decompression, true)
|
369
|
+
# Raise BadResponseError if response size does not match with Content-Length header in response. false by default.
|
370
|
+
# TODO: enable by default
|
371
|
+
attr_proxy(:strict_response_size_check, true)
|
358
372
|
# Local socket address. Set HTTPClient#socket_local.host and HTTPClient#socket_local.port to specify local binding hostname and port of TCP socket.
|
359
373
|
attr_proxy(:socket_local, true)
|
360
374
|
|
@@ -383,10 +397,25 @@ class HTTPClient
|
|
383
397
|
#
|
384
398
|
# After you set :base_url, all resources you pass to get, post and other
|
385
399
|
# methods are recognized to be prefixed with base_url. Say base_url is
|
386
|
-
# 'https://api.example.com/v1
|
400
|
+
# 'https://api.example.com/v1/, get('users') is the same as
|
387
401
|
# get('https://api.example.com/v1/users') internally. You can also pass
|
388
402
|
# full URL from 'http://' even after setting base_url.
|
389
403
|
#
|
404
|
+
# The expected base_url and path behavior is the following. Please take
|
405
|
+
# care of '/' in base_url and path.
|
406
|
+
#
|
407
|
+
# The last '/' is important for base_url:
|
408
|
+
# 1. http://foo/bar/baz/ + path -> http://foo/bar/baz/path
|
409
|
+
# 2. http://foo/bar/baz + path -> http://foo/bar/path
|
410
|
+
# Relative path handling:
|
411
|
+
# 3. http://foo/bar/baz/ + ../path -> http://foo/bar/path
|
412
|
+
# 4. http://foo/bar/baz + ../path -> http://foo/path
|
413
|
+
# 5. http://foo/bar/baz/ + ./path -> http://foo/bar/baz/path
|
414
|
+
# 6. http://foo/bar/baz + ./path -> http://foo/bar/path
|
415
|
+
# The leading '/' of path means absolute path:
|
416
|
+
# 7. http://foo/bar/baz/ + /path -> http://foo/path
|
417
|
+
# 8. http://foo/bar/baz + /path -> http://foo/path
|
418
|
+
#
|
390
419
|
# :default_header is for providing default headers Hash that all HTTP
|
391
420
|
# requests should have, such as custom 'Authorization' header in API.
|
392
421
|
# You can override :default_header with :header Hash parameter in HTTP
|
@@ -396,7 +425,7 @@ class HTTPClient
|
|
396
425
|
# HTTP client must send Authorization header after it gets 401 error
|
397
426
|
# from server from security reason. But in some situation (e.g. API
|
398
427
|
# client) you might want to send Authorization from the beginning.
|
399
|
-
def initialize(*args)
|
428
|
+
def initialize(*args, &block)
|
400
429
|
proxy, agent_name, from, base_url, default_header, force_basic_auth =
|
401
430
|
keyword_argument(args, :proxy, :agent_name, :from, :base_url, :default_header, :force_basic_auth)
|
402
431
|
@proxy = nil # assigned later.
|
@@ -420,6 +449,7 @@ class HTTPClient
|
|
420
449
|
load_environment
|
421
450
|
self.proxy = proxy if proxy
|
422
451
|
keep_webmock_compat
|
452
|
+
instance_eval(&block) if block
|
423
453
|
end
|
424
454
|
|
425
455
|
# webmock 1.6.2 depends on HTTP::Message#body.content to work.
|
@@ -692,9 +722,9 @@ class HTTPClient
|
|
692
722
|
def default_redirect_uri_callback(uri, res)
|
693
723
|
newuri = urify(res.header['location'][0])
|
694
724
|
if !http?(newuri) && !https?(newuri)
|
695
|
-
newuri
|
696
|
-
warn("could be a relative URI in location header which is not recommended")
|
725
|
+
warn("#{newuri}: a relative URI in location header which is not recommended")
|
697
726
|
warn("'The field value consists of a single absolute URI' in HTTP spec")
|
727
|
+
newuri = uri + newuri
|
698
728
|
end
|
699
729
|
if https?(uri) && !https?(newuri)
|
700
730
|
raise BadResponseError.new("redirecting to non-https resource")
|
@@ -713,6 +743,16 @@ class HTTPClient
|
|
713
743
|
request(:get, uri, argument_to_hash(args, :query, :header, :follow_redirect), &block)
|
714
744
|
end
|
715
745
|
|
746
|
+
# Sends PATCH request to the specified URL. See request for arguments.
|
747
|
+
def patch(uri, *args, &block)
|
748
|
+
if hashy_argument_has_keys(args, :query, :body)
|
749
|
+
new_args = args[0]
|
750
|
+
else
|
751
|
+
new_args = argument_to_hash(args, :body, :header)
|
752
|
+
end
|
753
|
+
request(:patch, uri, new_args, &block)
|
754
|
+
end
|
755
|
+
|
716
756
|
# Sends POST request to the specified URL. See request for arguments.
|
717
757
|
# You should not depend on :follow_redirect => true for POST method. It
|
718
758
|
# sends the same POST method to the new location which is prohibited in HTTP spec.
|
@@ -808,13 +848,7 @@ class HTTPClient
|
|
808
848
|
end
|
809
849
|
uri = to_resource_url(uri)
|
810
850
|
if block
|
811
|
-
|
812
|
-
filtered_block = proc { |res, str|
|
813
|
-
block.call(str)
|
814
|
-
}
|
815
|
-
else
|
816
|
-
filtered_block = block
|
817
|
-
end
|
851
|
+
filtered_block = adapt_block(&block)
|
818
852
|
end
|
819
853
|
if follow_redirect
|
820
854
|
follow_redirect(method, uri, query, body, header, &block)
|
@@ -835,6 +869,17 @@ class HTTPClient
|
|
835
869
|
request_async2(:get, uri, argument_to_hash(args, :query, :header))
|
836
870
|
end
|
837
871
|
|
872
|
+
# Sends PATCH request in async style. See request_async2 for arguments.
|
873
|
+
# It immediately returns a HTTPClient::Connection instance as a result.
|
874
|
+
def patch_async(uri, *args)
|
875
|
+
if hashy_argument_has_keys(args, :query, :body)
|
876
|
+
new_args = args[0]
|
877
|
+
else
|
878
|
+
new_args = argument_to_hash(args, :body, :header)
|
879
|
+
end
|
880
|
+
request_async2(:patch, uri, new_args)
|
881
|
+
end
|
882
|
+
|
838
883
|
# Sends POST request in async style. See request_async for arguments.
|
839
884
|
# It immediately returns a HTTPClient::Connection instance as a result.
|
840
885
|
def post_async(uri, *args)
|
@@ -1035,11 +1080,17 @@ private
|
|
1035
1080
|
ENV[name.downcase] || ENV[name.upcase]
|
1036
1081
|
end
|
1037
1082
|
|
1083
|
+
def adapt_block(&block)
|
1084
|
+
return block if block.arity == 2
|
1085
|
+
proc { |r, str| block.call(str) }
|
1086
|
+
end
|
1087
|
+
|
1038
1088
|
def follow_redirect(method, uri, query, body, header, &block)
|
1039
1089
|
uri = to_resource_url(uri)
|
1040
1090
|
if block
|
1091
|
+
b = adapt_block(&block)
|
1041
1092
|
filtered_block = proc { |r, str|
|
1042
|
-
|
1093
|
+
b.call(r, str) if r.ok?
|
1043
1094
|
}
|
1044
1095
|
end
|
1045
1096
|
if HTTP::Message.file?(body)
|
@@ -1080,7 +1131,7 @@ private
|
|
1080
1131
|
def protect_keep_alive_disconnected
|
1081
1132
|
begin
|
1082
1133
|
yield
|
1083
|
-
rescue KeepAliveDisconnected
|
1134
|
+
rescue KeepAliveDisconnected
|
1084
1135
|
# Force to create new connection
|
1085
1136
|
Thread.current[:HTTPClient_AcquireNewConnection] = true
|
1086
1137
|
begin
|
@@ -1101,7 +1152,7 @@ private
|
|
1101
1152
|
boundary = nil
|
1102
1153
|
if body
|
1103
1154
|
_, content_type = header.find { |key, value|
|
1104
|
-
key.downcase == 'content-type'
|
1155
|
+
key.to_s.downcase == 'content-type'
|
1105
1156
|
}
|
1106
1157
|
if content_type
|
1107
1158
|
if /\Amultipart/ =~ content_type
|
@@ -1110,7 +1161,7 @@ private
|
|
1110
1161
|
else
|
1111
1162
|
boundary = create_boundary
|
1112
1163
|
content_type = "#{content_type}; boundary=#{boundary}"
|
1113
|
-
header = override_header(header, '
|
1164
|
+
header = override_header(header, 'content-type', content_type)
|
1114
1165
|
end
|
1115
1166
|
end
|
1116
1167
|
else
|
@@ -1148,7 +1199,7 @@ private
|
|
1148
1199
|
def override_header(header, key, value)
|
1149
1200
|
result = []
|
1150
1201
|
header.each do |k, v|
|
1151
|
-
if k.downcase == key
|
1202
|
+
if k.to_s.downcase == key
|
1152
1203
|
result << [key, value]
|
1153
1204
|
else
|
1154
1205
|
result << [k, v]
|
@@ -1223,6 +1274,7 @@ private
|
|
1223
1274
|
return
|
1224
1275
|
end
|
1225
1276
|
piper, pipew = IO.pipe
|
1277
|
+
pipew.binmode
|
1226
1278
|
res = HTTP::Message.new_response(piper, req.header)
|
1227
1279
|
@debug_dev << "= Request\n\n" if @debug_dev
|
1228
1280
|
sess = @session_manager.query(req, proxy)
|
@@ -1267,7 +1319,7 @@ private
|
|
1267
1319
|
def to_resource_url(uri)
|
1268
1320
|
u = urify(uri)
|
1269
1321
|
if @base_url && u.scheme.nil? && u.host.nil?
|
1270
|
-
urify(@base_url + uri
|
1322
|
+
urify(@base_url) + uri
|
1271
1323
|
else
|
1272
1324
|
u
|
1273
1325
|
end
|
data/lib/oauthclient.rb
CHANGED
@@ -1,5 +1,5 @@
|
|
1
1
|
# HTTPClient - HTTP client library.
|
2
|
-
# Copyright (C) 2000-
|
2
|
+
# Copyright (C) 2000-2015 NAKAMURA, Hiroshi <nahi@ruby-lang.org>.
|
3
3
|
#
|
4
4
|
# This program is copyrighted free software by NAKAMURA, Hiroshi. You can
|
5
5
|
# redistribute it and/or modify it under the same terms of Ruby's license;
|
@@ -33,6 +33,7 @@ class OAuthClient < HTTPClient
|
|
33
33
|
@oauth_config = HTTPClient::OAuth::Config.new
|
34
34
|
self.www_auth.oauth.set_config(nil, @oauth_config)
|
35
35
|
self.www_auth.oauth.challenge(nil)
|
36
|
+
self.strict_response_size_check = true
|
36
37
|
end
|
37
38
|
|
38
39
|
# Get request token.
|
data/test/helper.rb
CHANGED
@@ -59,11 +59,13 @@ module Helper
|
|
59
59
|
@client = HTTPClient.new
|
60
60
|
end
|
61
61
|
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
62
|
+
def escape_noproxy
|
63
|
+
backup = HTTPClient::NO_PROXY_HOSTS.dup
|
64
|
+
HTTPClient::NO_PROXY_HOSTS.clear
|
65
|
+
yield
|
66
|
+
ensure
|
67
|
+
HTTPClient::NO_PROXY_HOSTS.replace(backup)
|
68
|
+
end
|
67
69
|
|
68
70
|
def setup_proxyserver
|
69
71
|
@proxyserver = WEBrick::HTTPProxyServer.new(
|
@@ -0,0 +1,32 @@
|
|
1
|
+
require File.expand_path('helper', File.join(File.dirname(__FILE__), ".."))
|
2
|
+
|
3
|
+
|
4
|
+
class PEMUtilsTest < Test::Unit::TestCase
|
5
|
+
include Helper
|
6
|
+
|
7
|
+
def setup
|
8
|
+
@raw_cert = "-----BEGIN CERTIFICATE-----\nMIIDOTCCAiGgAwIBAgIBAjANBgkqhkiG9w0BAQsFADBCMRMwEQYKCZImiZPyLGQB\nGRYDb3JnMRkwFwYKCZImiZPyLGQBGRYJcnVieS1sYW5nMRAwDgYDVQQDDAdSdWJ5\nIENBMB4XDTE2MDgxMDE3MjEzNFoXDTE3MDgxMDE3MjEzNFowSzETMBEGCgmSJomT\n8ixkARkWA29yZzEZMBcGCgmSJomT8ixkARkWCXJ1YnktbGFuZzEZMBcGA1UEAwwQ\nUnVieSBjZXJ0aWZpY2F0ZTCCASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEB\nAJCfsSXpSMpmZCVa+ZCM+QDgomnhDlvnrGDq6pasTaIspGTXgws+7r8Dt/cNe6EH\nHJpRH2cGRiO4yPcfcT9eS4X7k8OC4f33wHfACOmLu6LeoNE8ujmSk6L6WzLUI+sE\nnLZbFrXxoAo4XHsm8vEG9C+jEoXZ1p+47wrAGaDwDQTnzlMy4dT9pRQEJP2G/Rry\nUkuZn8SUWmh3/YS78iaSzsNF1cgE1ealHOrPPFDjiCGDaH/LHyUPYlbFSLZ/B7Qx\nLxi5sePLcywWq/EJrmWpgeVTDjtNijsdKv/A3qkY+fm/oD0pzt7XsfJaP9YKNyJO\nQFdxWZeiPcDF+Hwf+IwSr+kCAwEAAaMxMC8wDgYDVR0PAQH/BAQDAgeAMB0GA1Ud\nDgQWBBQNvzYzJyXemGhxbA8NMXLolDnPyjANBgkqhkiG9w0BAQsFAAOCAQEARIJV\noKejGlOTn71QutnNnu07UtTu0IHs6YqjYzzND+m4JXLN+wvYm72AFUG0b1L7dRg0\niK8XjQrlNQNVqP1Mc6tffchy20neOPOHeiO6qTdRU8P2S8D3Uwe+1qhgxjfE+cWc\nwZmWxYK4HA8c58PxWMqrkr2QqXDplG9KWLvOgrtPGiLLZcQSKhvvB63QzItHBDU6\nRayiJY3oPkK/HrIvFlySqFqzWmuyknkciOFywEHQMz/tcSFJ2QFpPj/tBz9VXohH\nZ8KscmfhZrTPBjo+ky1lz/WraWoz4LMiLnkC2ABczWLRSawu+v3Irx1NFJngt05e\npqwtqIUeg7j+JLiTaA==\n-----END CERTIFICATE-----"
|
9
|
+
end
|
10
|
+
|
11
|
+
def test_read_certificate
|
12
|
+
assert_nothing_raised do
|
13
|
+
binary = HTTPClient::JRubySSLSocket::PEMUtils.read_certificate(@raw_cert)
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
def test_read_certificate_works_with_random_ascii_text_outside_begin_end
|
18
|
+
raw_cert_with_ascii = "some text before begin\n" + @raw_cert + "\nsome text after end"
|
19
|
+
assert_nothing_raised do
|
20
|
+
binary = HTTPClient::JRubySSLSocket::PEMUtils.read_certificate(raw_cert_with_ascii)
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
def test_read_certificate_uses_all_content_if_missing_begin_end
|
25
|
+
cert = @raw_cert.sub(/-----BEGIN CERTIFICATE-----/, '').sub(/-----END CERTIFICATE-----/, '')
|
26
|
+
assert_nothing_raised do
|
27
|
+
binary = HTTPClient::JRubySSLSocket::PEMUtils.read_certificate(cert)
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
|
32
|
+
end
|
data/test/test_auth.rb
CHANGED
@@ -2,7 +2,6 @@ require File.expand_path('helper', File.dirname(__FILE__))
|
|
2
2
|
require 'digest/md5'
|
3
3
|
require 'rack'
|
4
4
|
require 'rack/lint'
|
5
|
-
require 'rack/showexceptions'
|
6
5
|
require 'rack-ntlm'
|
7
6
|
|
8
7
|
class TestAuth < Test::Unit::TestCase
|
@@ -124,6 +123,7 @@ class TestAuth < Test::Unit::TestCase
|
|
124
123
|
end
|
125
124
|
# Make it work if @value == nil
|
126
125
|
class SecurityBuffer < FieldSet
|
126
|
+
remove_method(:data_size) if method_defined?(:data_size)
|
127
127
|
def data_size
|
128
128
|
@active && @value ? @value.size : 0
|
129
129
|
end
|
@@ -230,7 +230,7 @@ class TestAuth < Test::Unit::TestCase
|
|
230
230
|
c.www_auth.basic_auth.instance_eval { @scheme = "BASIC" }
|
231
231
|
c.set_auth("http://localhost:#{serverport}/", 'admin', 'admin')
|
232
232
|
|
233
|
-
|
233
|
+
100.times.map { |idx|
|
234
234
|
Thread.new(idx) { |idx2|
|
235
235
|
Thread.abort_on_exception = true
|
236
236
|
Thread.pass
|
@@ -251,7 +251,7 @@ class TestAuth < Test::Unit::TestCase
|
|
251
251
|
c.test_loopback_http_response << "HTTP/1.0 200 OK\nContent-Length: 2\n\nOK"
|
252
252
|
c.debug_dev = str = ''
|
253
253
|
c.get_content("http://localhost:#{serverport}/basic_auth/sub/dir/")
|
254
|
-
assert_match
|
254
|
+
assert_match(/Authorization: Basic YWRtaW46YWRtaW4=/, str)
|
255
255
|
end
|
256
256
|
|
257
257
|
def test_digest_auth
|
@@ -267,7 +267,7 @@ class TestAuth < Test::Unit::TestCase
|
|
267
267
|
c.test_loopback_http_response << "HTTP/1.0 200 OK\nContent-Length: 2\n\nOK"
|
268
268
|
c.debug_dev = str = ''
|
269
269
|
c.get_content("http://localhost:#{serverport}/digest_auth/sub/dir/")
|
270
|
-
assert_match
|
270
|
+
assert_match(/Authorization: Digest/, str)
|
271
271
|
end
|
272
272
|
|
273
273
|
def test_digest_auth_with_block
|
@@ -332,6 +332,16 @@ class TestAuth < Test::Unit::TestCase
|
|
332
332
|
assert_match(/Proxy-Authorization: Basic YWRtaW46YWRtaW4=/, str)
|
333
333
|
end
|
334
334
|
|
335
|
+
def test_proxy_auth_force
|
336
|
+
c = HTTPClient.new
|
337
|
+
c.set_proxy_auth('admin', 'admin')
|
338
|
+
c.force_basic_auth = true
|
339
|
+
c.test_loopback_http_response << "HTTP/1.0 200 OK\nContent-Length: 2\n\nOK"
|
340
|
+
c.debug_dev = str = ''
|
341
|
+
c.get_content('http://example.com/')
|
342
|
+
assert_match(/Proxy-Authorization: Basic YWRtaW46YWRtaW4=/, str)
|
343
|
+
end
|
344
|
+
|
335
345
|
def test_proxy_auth_reuses_credentials
|
336
346
|
c = HTTPClient.new
|
337
347
|
c.set_proxy_auth('admin', 'admin')
|
@@ -442,11 +452,20 @@ class TestAuth < Test::Unit::TestCase
|
|
442
452
|
end
|
443
453
|
|
444
454
|
def test_basic_auth_post_with_multipart
|
445
|
-
|
446
|
-
|
447
|
-
|
448
|
-
|
449
|
-
|
455
|
+
retry_times = 0
|
456
|
+
begin
|
457
|
+
c = HTTPClient.new
|
458
|
+
c.set_auth("http://localhost:#{serverport}/", 'admin', 'admin')
|
459
|
+
File.open(__FILE__) do |f|
|
460
|
+
# read 'f' twice for authorization negotiation
|
461
|
+
assert_equal('basic_auth OK', c.post("http://localhost:#{serverport}/basic_auth", :file => f).content)
|
462
|
+
end
|
463
|
+
rescue Errno::ECONNRESET, HTTPClient::KeepAliveDisconnected
|
464
|
+
# TODO: WEBrick server returns ECONNRESET/EPIPE before sending Unauthorized response to client?
|
465
|
+
raise if retry_times > 5
|
466
|
+
retry_times += 1
|
467
|
+
sleep 1
|
468
|
+
retry
|
450
469
|
end
|
451
470
|
end
|
452
471
|
|
data/test/test_cookie.rb
CHANGED
@@ -290,8 +290,8 @@ EOF
|
|
290
290
|
def test_load_cookies_escaped
|
291
291
|
uri = urify('http://example.org/')
|
292
292
|
f = Tempfile.new('test_cookie')
|
293
|
-
File.open(f.path, 'w') do |
|
294
|
-
|
293
|
+
File.open(f.path, 'w') do |out|
|
294
|
+
out.write <<EOF
|
295
295
|
http://example.org/ key1 "value" 0 .example.org / 13 0
|
296
296
|
http://example.org/ key2 "" 0 .example.org / 13 0
|
297
297
|
http://example.org/ key3 0 .example.org / 13 0
|
data/test/test_http-access2.rb
CHANGED
@@ -347,11 +347,13 @@ class TestClient < Test::Unit::TestCase
|
|
347
347
|
def test_receive_timeout
|
348
348
|
# this test takes 2 sec
|
349
349
|
assert_equal('hello', @client.get_content(serverurl + 'sleep?sec=2'))
|
350
|
+
@client.reset_all
|
350
351
|
@client.receive_timeout = 1
|
351
352
|
assert_equal('hello', @client.get_content(serverurl + 'sleep?sec=0'))
|
352
353
|
assert_raise(HTTPClient::ReceiveTimeoutError) do
|
353
354
|
@client.get_content(serverurl + 'sleep?sec=2')
|
354
355
|
end
|
356
|
+
@client.reset_all
|
355
357
|
@client.receive_timeout = 3
|
356
358
|
assert_equal('hello', @client.get_content(serverurl + 'sleep?sec=2'))
|
357
359
|
end
|