httpclient-jgraichen 2.3.4.2

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.
Files changed (58) hide show
  1. checksums.yaml +7 -0
  2. data/README.txt +759 -0
  3. data/bin/httpclient +65 -0
  4. data/lib/hexdump.rb +50 -0
  5. data/lib/http-access2.rb +55 -0
  6. data/lib/http-access2/cookie.rb +1 -0
  7. data/lib/http-access2/http.rb +1 -0
  8. data/lib/httpclient.rb +1156 -0
  9. data/lib/httpclient/auth.rb +899 -0
  10. data/lib/httpclient/cacert.p7s +1912 -0
  11. data/lib/httpclient/connection.rb +88 -0
  12. data/lib/httpclient/cookie.rb +438 -0
  13. data/lib/httpclient/http.rb +1046 -0
  14. data/lib/httpclient/include_client.rb +83 -0
  15. data/lib/httpclient/session.rb +1028 -0
  16. data/lib/httpclient/ssl_config.rb +405 -0
  17. data/lib/httpclient/timeout.rb +140 -0
  18. data/lib/httpclient/util.rb +178 -0
  19. data/lib/httpclient/version.rb +3 -0
  20. data/lib/oauthclient.rb +110 -0
  21. data/sample/async.rb +8 -0
  22. data/sample/auth.rb +11 -0
  23. data/sample/cookie.rb +18 -0
  24. data/sample/dav.rb +103 -0
  25. data/sample/howto.rb +49 -0
  26. data/sample/oauth_buzz.rb +57 -0
  27. data/sample/oauth_friendfeed.rb +59 -0
  28. data/sample/oauth_twitter.rb +61 -0
  29. data/sample/ssl/0cert.pem +22 -0
  30. data/sample/ssl/0key.pem +30 -0
  31. data/sample/ssl/1000cert.pem +19 -0
  32. data/sample/ssl/1000key.pem +18 -0
  33. data/sample/ssl/htdocs/index.html +10 -0
  34. data/sample/ssl/ssl_client.rb +22 -0
  35. data/sample/ssl/webrick_httpsd.rb +29 -0
  36. data/sample/stream.rb +21 -0
  37. data/sample/thread.rb +27 -0
  38. data/sample/wcat.rb +21 -0
  39. data/test/ca-chain.cert +44 -0
  40. data/test/ca.cert +23 -0
  41. data/test/client.cert +19 -0
  42. data/test/client.key +15 -0
  43. data/test/helper.rb +129 -0
  44. data/test/htdigest +1 -0
  45. data/test/htpasswd +2 -0
  46. data/test/runner.rb +2 -0
  47. data/test/server.cert +19 -0
  48. data/test/server.key +15 -0
  49. data/test/sslsvr.rb +65 -0
  50. data/test/subca.cert +21 -0
  51. data/test/test_auth.rb +348 -0
  52. data/test/test_cookie.rb +412 -0
  53. data/test/test_hexdump.rb +14 -0
  54. data/test/test_http-access2.rb +507 -0
  55. data/test/test_httpclient.rb +1783 -0
  56. data/test/test_include_client.rb +52 -0
  57. data/test/test_ssl.rb +235 -0
  58. metadata +100 -0
@@ -0,0 +1,412 @@
1
+ require 'test/unit'
2
+ require 'uri'
3
+
4
+ require 'httpclient/cookie'
5
+
6
+ class TestCookie < Test::Unit::TestCase
7
+ include HTTPClient::Util
8
+
9
+ def setup()
10
+ @c = WebAgent::Cookie.new()
11
+ end
12
+
13
+ def test_s_new()
14
+ assert_instance_of(WebAgent::Cookie, @c)
15
+ end
16
+
17
+ def test_discard?
18
+ assert_equal(false, !!(@c.discard?))
19
+ @c.discard = true
20
+ assert_equal(true, !!(@c.discard?))
21
+ end
22
+
23
+ def test_match()
24
+ url = urify('http://www.rubycolor.org/hoge/funi/#919191')
25
+
26
+ @c.domain = 'www.rubycolor.org'
27
+ assert_equal(true, @c.match?(url))
28
+
29
+ @c.domain = '.rubycolor.org'
30
+ assert_equal(true, @c.match?(url))
31
+
32
+ @c.domain = 'aaa.www.rubycolor.org'
33
+ assert_equal(false, @c.match?(url))
34
+
35
+ @c.domain = 'aaa.www.rubycolor.org'
36
+ assert_equal(false, @c.match?(url))
37
+
38
+ @c.domain = 'www.rubycolor.org'
39
+ @c.path = '/'
40
+ assert_equal(true, @c.match?(url))
41
+
42
+ @c.domain = 'www.rubycolor.org'
43
+ @c.path = '/hoge'
44
+ assert_equal(true, @c.match?(url))
45
+
46
+ @c.domain = 'www.rubycolor.org'
47
+ @c.path = '/hoge/hoge'
48
+ assert_equal(false, @c.match?(url))
49
+
50
+ @c.domain = 'www.rubycolor.org'
51
+ @c.path = '/hoge'
52
+ @c.secure = true
53
+ assert_equal(false, @c.match?(url))
54
+
55
+ url2 = urify('https://www.rubycolor.org/hoge/funi/#919191')
56
+ @c.domain = 'www.rubycolor.org'
57
+ @c.path = '/hoge'
58
+ @c.secure = true
59
+ assert_equal(true, @c.match?(url2))
60
+
61
+ @c.domain = 'www.rubycolor.org'
62
+ @c.path = '/hoge'
63
+ @c.secure = nil
64
+ assert_equal(true, @c.match?(url2)) ## not false!
65
+
66
+ url.port = 80
67
+ @c.domain = 'www.rubycolor.org'
68
+ @c.path = '/hoge'
69
+ # @c.port = [80,8080]
70
+ assert_equal(true, @c.match?(url))
71
+
72
+ url_nopath = URI.parse('http://www.rubycolor.org')
73
+ @c.domain = 'www.rubycolor.org'
74
+ @c.path = '/'
75
+ assert_equal(true, @c.match?(url_nopath))
76
+
77
+ end
78
+
79
+ def test_head_match?()
80
+ assert_equal(true, @c.head_match?("",""))
81
+ assert_equal(false, @c.head_match?("a",""))
82
+ assert_equal(true, @c.head_match?("","a"))
83
+ assert_equal(true, @c.head_match?("abcde","abcde"))
84
+ assert_equal(true, @c.head_match?("abcde","abcdef"))
85
+ assert_equal(false, @c.head_match?("abcdef","abcde"))
86
+ assert_equal(false, @c.head_match?("abcde","bcde"))
87
+ assert_equal(false, @c.head_match?("bcde","abcde"))
88
+ end
89
+
90
+ def test_tail_match?()
91
+ assert_equal(true, @c.tail_match?("",""))
92
+ assert_equal(false, @c.tail_match?("a",""))
93
+ assert_equal(true, @c.tail_match?("","a"))
94
+ assert_equal(true, @c.tail_match?("abcde","abcde"))
95
+ assert_equal(false, @c.tail_match?("abcde","abcdef"))
96
+ assert_equal(false, @c.tail_match?("abcdef","abcde"))
97
+ assert_equal(false, @c.tail_match?("abcde","bcde"))
98
+ assert_equal(true, @c.tail_match?("bcde","abcde"))
99
+ end
100
+
101
+
102
+ def test_domain_match()
103
+ extend WebAgent::CookieUtils
104
+ assert_equal(true, !!domain_match("hoge.co.jp","."))
105
+ # assert_equal(true, !!domain_match("locahost",".local"))
106
+ assert_equal(true, !!domain_match("192.168.10.1","192.168.10.1"))
107
+ assert_equal(false, !!domain_match("192.168.10.1","192.168.10.2"))
108
+ # assert_equal(false, !!domain_match("hoge.co.jp",".hoge.co.jp"))
109
+ # allows; host == rubyforge.org, domain == .rubyforge.org
110
+ assert_equal(true, !!domain_match("hoge.co.jp",".hoge.co.jp"))
111
+ assert_equal(true, !!domain_match("www.hoge.co.jp", "www.hoge.co.jp"))
112
+ assert_equal(false, !!domain_match("www.hoge.co.jp", "www2.hoge.co.jp"))
113
+ assert_equal(true, !!domain_match("www.hoge.co.jp", ".hoge.co.jp"))
114
+ assert_equal(true, !!domain_match("www.aa.hoge.co.jp", ".hoge.co.jp"))
115
+ assert_equal(false, !!domain_match("www.hoge.co.jp", "hoge.co.jp"))
116
+ end
117
+
118
+ def test_join_quotedstr()
119
+ arr1 = ['hoge=funi', 'hoge2=funi2']
120
+ assert_equal(arr1, @c.instance_eval{join_quotedstr(arr1,';')})
121
+ arr2 = ['hoge="fu', 'ni"', 'funi=funi']
122
+ assert_equal(['hoge="fu;ni"','funi=funi'],
123
+ @c.instance_eval{join_quotedstr(arr2,';')})
124
+ arr3 = ['hoge="funi";hoge2="fu','ni2";hoge3="hoge"', 'funi="funi"']
125
+ assert_equal(['hoge="funi";hoge2="fu,ni2";hoge3="hoge"', 'funi="funi"'],
126
+ @c.instance_eval{join_quotedstr(arr3,',')})
127
+ end
128
+
129
+ end
130
+
131
+ class TestCookieManager < Test::Unit::TestCase
132
+ include HTTPClient::Util
133
+
134
+ def setup()
135
+ @cm = WebAgent::CookieManager.new()
136
+ end
137
+
138
+ def teardown()
139
+ end
140
+
141
+ def test_parse()
142
+ str = "inkid=n92b0ADOgACIgUb9lsjHqAAAHu2a; expires=Wed, 01-Dec-2010 00:00:00 GMT; path=/"
143
+ @cm.parse(str, urify('http://www.test.jp'))
144
+ cookie = @cm.cookies[0]
145
+ assert_instance_of(WebAgent::Cookie, cookie)
146
+ assert_equal("inkid", cookie.name)
147
+ assert_equal("n92b0ADOgACIgUb9lsjHqAAAHu2a", cookie.value)
148
+ assert_equal(Time.gm(2010, 12, 1, 0,0,0), cookie.expires)
149
+ assert_equal("/", cookie.path)
150
+ end
151
+
152
+ def test_parse2()
153
+ str = "xmen=off,0,0,1; path=/; domain=.excite.co.jp; expires=Wednesday, 31-Dec-2037 12:00:00 GMT"
154
+ @cm.parse(str, urify('http://www.excite.co.jp'))
155
+ cookie = @cm.cookies[0]
156
+ assert_instance_of(WebAgent::Cookie, cookie)
157
+ assert_equal("xmen", cookie.name)
158
+ assert_equal("off,0,0,1", cookie.value)
159
+ assert_equal("/", cookie.path)
160
+ assert_equal(".excite.co.jp", cookie.domain)
161
+ assert_equal(Time.gm(2037,12,31,12,0,0), cookie.expires)
162
+ end
163
+
164
+ def test_parse3()
165
+ str = "xmen=off,0,0,1; path=/; domain=.excite.co.jp; expires=Wednesday, 31-Dec-2037 12:00:00 GMT;Secure;HTTPOnly"
166
+ @cm.parse(str, urify('http://www.excite.co.jp'))
167
+ cookie = @cm.cookies[0]
168
+ assert_instance_of(WebAgent::Cookie, cookie)
169
+ assert_equal("xmen", cookie.name)
170
+ assert_equal("off,0,0,1", cookie.value)
171
+ assert_equal("/", cookie.path)
172
+ assert_equal(".excite.co.jp", cookie.domain)
173
+ assert_equal(Time.gm(2037,12,31,12,0,0), cookie.expires)
174
+ assert_equal(true, cookie.secure?)
175
+ assert_equal(true, cookie.http_only?)
176
+ end
177
+
178
+ def test_parse_double_semicolon()
179
+ str = "xmen=off,0,0,1;; path=\"/;;\"; domain=.excite.co.jp; expires=Wednesday, 31-Dec-2037 12:00:00 GMT"
180
+ @cm.parse(str, urify('http://www.excite.co.jp'))
181
+ cookie = @cm.cookies[0]
182
+ assert_instance_of(WebAgent::Cookie, cookie)
183
+ assert_equal("xmen", cookie.name)
184
+ assert_equal("off,0,0,1", cookie.value)
185
+ assert_equal("/;;", cookie.path)
186
+ assert_equal(".excite.co.jp", cookie.domain)
187
+ assert_equal(Time.gm(2037,12,31,12,0,0), cookie.expires)
188
+ end
189
+
190
+ # def test_make_portlist()
191
+ # assert_equal([80,8080], @cm.instance_eval{make_portlist("80,8080")})
192
+ # assert_equal([80], @cm.instance_eval{make_portlist("80")})
193
+ # assert_equal([80,8080,10080], @cm.instance_eval{make_portlist(" 80, 8080, 10080 \n")})
194
+ # end
195
+
196
+ def test_check_expired_cookies()
197
+ c1 = WebAgent::Cookie.new()
198
+ c2 = c1.dup
199
+ c3 = c1.dup
200
+ c4 = c1.dup
201
+ c1.expires = Time.now - 100
202
+ c2.expires = Time.now + 100
203
+ c3.expires = Time.now - 10
204
+ c4.expires = nil
205
+ cookies = [c1,c2,c3,c4]
206
+ @cm.cookies = cookies
207
+ @cm.check_expired_cookies()
208
+ # expires == nil cookies (session cookie) exists.
209
+ assert_equal([c2,c4], @cm.cookies)
210
+ end
211
+
212
+ def test_parse_expires
213
+ str = "inkid=n92b0ADOgACIgUb9lsjHqAAAHu2a; expires=; path=/"
214
+ @cm.parse(str, urify('http://www.test.jp'))
215
+ cookie = @cm.cookies[0]
216
+ assert_equal("inkid", cookie.name)
217
+ assert_equal("n92b0ADOgACIgUb9lsjHqAAAHu2a", cookie.value)
218
+ assert_equal(nil, cookie.expires)
219
+ assert_equal("/", cookie.path)
220
+ #
221
+ str = "inkid=n92b0ADOgACIgUb9lsjHqAAAHu2a; path=/; expires="
222
+ @cm.parse(str, urify('http://www.test.jp'))
223
+ cookie = @cm.cookies[0]
224
+ assert_equal("inkid", cookie.name)
225
+ assert_equal("n92b0ADOgACIgUb9lsjHqAAAHu2a", cookie.value)
226
+ assert_equal(nil, cookie.expires)
227
+ assert_equal("/", cookie.path)
228
+ #
229
+ str = "inkid=n92b0ADOgACIgUb9lsjHqAAAHu2a; path=/; expires=\"\""
230
+ @cm.parse(str, urify('http://www.test.jp'))
231
+ cookie = @cm.cookies[0]
232
+ assert_equal("inkid", cookie.name)
233
+ assert_equal("n92b0ADOgACIgUb9lsjHqAAAHu2a", cookie.value)
234
+ assert_equal(nil, cookie.expires)
235
+ assert_equal("/", cookie.path)
236
+ end
237
+
238
+ def test_parse_after_expiration
239
+ str = "inkid=n92b0ADOgACIgUb9lsjHqAAAHu2a; expires=Wed, 01-Dec-2010 00:00:00 GMT; path=/"
240
+ @cm.parse(str, urify('http://www.test.jp'))
241
+ cookie = @cm.cookies[0]
242
+ assert_instance_of(WebAgent::Cookie, cookie)
243
+ assert_equal("inkid", cookie.name)
244
+ assert_equal("n92b0ADOgACIgUb9lsjHqAAAHu2a", cookie.value)
245
+ assert_equal(Time.gm(2010, 12, 1, 0,0,0), cookie.expires)
246
+ assert_equal("/", cookie.path)
247
+
248
+ time = Time.now.utc.round + 60
249
+ expires = time.strftime("%a, %d-%b-%Y %H:%M:%S GMT")
250
+ str = "inkid=n92b0ADOgACIgUb9lsjHqAAAHu2a; expires=#{expires}; path=/"
251
+ @cm.parse(str, urify('http://www.test.jp'))
252
+ cookie = @cm.cookies[0]
253
+ assert_equal("inkid", cookie.name)
254
+ assert_equal("n92b0ADOgACIgUb9lsjHqAAAHu2a", cookie.value)
255
+ assert_equal(time, cookie.expires)
256
+ assert_equal("/", cookie.path)
257
+ end
258
+
259
+ def test_find_cookie()
260
+ str = "xmen=off,0,0,1; path=/; domain=.excite2.co.jp; expires=Wednesday, 31-Dec-2037 12:00:00 GMT"
261
+ @cm.parse(str, urify("http://www.excite2.co.jp/"))
262
+
263
+ str = "xmen=off,0,0,2; path=/; domain=.excite.co.jp; expires=Wednesday, 31-Dec-2037 12:00:00 GMT"
264
+ @cm.parse(str, urify("http://www.excite.co.jp/"))
265
+
266
+ @cm.cookies[0].use = true
267
+ @cm.cookies[1].use = true
268
+
269
+ url = urify('http://www.excite.co.jp/hoge/funi/')
270
+ cookie_str = @cm.find(url)
271
+ assert_equal("xmen=off,0,0,2", cookie_str)
272
+ end
273
+
274
+ def test_load_cookies()
275
+ begin
276
+ File.open("tmp_test.tmp","w") {|f|
277
+ f.write <<EOF
278
+ http://www.zdnet.co.jp/news/0106/08/e_gibson.html NGUserID d29b8f49-10875-992421294-1 2145801600 www.zdnet.co.jp / 9 0
279
+ http://www.zdnet.co.jp/news/0106/08/e_gibson.html PACK zd3-992421294-7436 1293839999 .zdnet.co.jp / 13 0
280
+ http://example.org/ key value 0 .example.org / 13 0
281
+ http://example.org/ key value .example.org / 13 0
282
+ EOF
283
+ }
284
+
285
+ @cm.cookies_file = 'tmp_test.tmp'
286
+ @cm.load_cookies()
287
+ c0, c1, c2, c3 = @cm.cookies
288
+ assert_equal('http://www.zdnet.co.jp/news/0106/08/e_gibson.html', c0.url.to_s)
289
+ assert_equal('NGUserID', c0.name)
290
+ assert_equal('d29b8f49-10875-992421294-1', c0.value)
291
+ assert_equal(Time.at(2145801600), c0.expires)
292
+ assert_equal('www.zdnet.co.jp', c0.domain)
293
+ assert_equal('/', c0.path)
294
+ assert_equal(9, c0.flag)
295
+ #
296
+ assert_equal('http://www.zdnet.co.jp/news/0106/08/e_gibson.html', c1.url.to_s)
297
+ assert_equal('PACK', c1.name)
298
+ assert_equal('zd3-992421294-7436', c1.value)
299
+ assert_equal(Time.at(1293839999), c1.expires)
300
+ assert_equal('.zdnet.co.jp', c1.domain)
301
+ assert_equal('/', c1.path)
302
+ assert_equal(13, c1.flag)
303
+ #
304
+ assert_equal(nil, c2.expires)
305
+ assert_equal(nil, c3.expires) # allow empty 'expires' (should not happen)
306
+ ensure
307
+ File.unlink("tmp_test.tmp")
308
+ end
309
+ end
310
+
311
+ def test_save_cookie()
312
+ str = <<EOF
313
+ http://www.zdnet.co.jp/news/0106/08/e_gibson.html NGUserID d29b8f49-10875-992421294-1 2145801600 www.zdnet.co.jp / 9
314
+ http://www.zdnet.co.jp/news/0106/08/e_gibson.html PACK zd3-992421294-7436 2145801600 .zdnet.co.jp / 13
315
+ EOF
316
+ begin
317
+ File.open("tmp_test.tmp","w") {|f|
318
+ f.write str
319
+ }
320
+ @cm.cookies_file = 'tmp_test.tmp'
321
+ @cm.load_cookies()
322
+ @cm.instance_eval{@is_saved = false}
323
+ @cm.cookies_file = 'tmp_test2.tmp'
324
+ @cm.save_cookies()
325
+ str2 = ''
326
+ File.open("tmp_test2.tmp","r") {|f|
327
+ str2 = f.read()
328
+ }
329
+ assert_equal(str, str2)
330
+ #
331
+ assert(File.exist?('tmp_test2.tmp'))
332
+ File.unlink("tmp_test2.tmp")
333
+ @cm.save_cookies()
334
+ assert(!File.exist?('tmp_test2.tmp'))
335
+ @cm.save_cookies(true)
336
+ assert(File.exist?('tmp_test2.tmp'))
337
+ ensure
338
+ File.unlink("tmp_test.tmp")
339
+ if FileTest.exist?("tmp_test2.tmp")
340
+ File.unlink("tmp_test2.tmp")
341
+ end
342
+ end
343
+ end
344
+
345
+ def test_not_saved_expired_cookies
346
+ begin
347
+ @cm.cookies_file = 'tmp_test.tmp'
348
+ uri = urify('http://www.example.org')
349
+ @cm.parse("foo=1; path=/", uri)
350
+ @cm.parse("bar=2; path=/; expires=", uri)
351
+ @cm.parse("baz=3; path=/; expires=\"\"", uri)
352
+ @cm.parse("qux=4; path=/; expires=#{(Time.now + 10).asctime}", uri)
353
+ @cm.parse("quxx=5; path=/; expires=#{(Time.now - 10).asctime}", uri)
354
+ @cm.save_cookies()
355
+ @cm.load_cookies
356
+ assert_equal(1, @cm.cookies.size) # +10 cookies only
357
+ ensure
358
+ File.unlink("tmp_test.tmp") if File.exist?("tmp_test.tmp")
359
+ end
360
+ end
361
+
362
+ def test_add()
363
+ c = WebAgent::Cookie.new()
364
+ c.name = "hoge"
365
+ c.value = "funi"
366
+ c.url = urify("http://www.inac.co.jp/hoge")
367
+ @cm.add(c)
368
+ c = @cm.cookies[0]
369
+ assert_equal('hoge', c.name)
370
+ assert_equal('funi', c.value)
371
+ assert_equal(nil, c.expires)
372
+ end
373
+
374
+ def test_add2()
375
+ c = WebAgent::Cookie.new()
376
+ c.name = "hoge"
377
+ c.value = "funi"
378
+ c.path = ''
379
+ c.url = urify("http://www.inac.co.jp/hoge/hoge2/hoge3")
380
+ @cm.add(c)
381
+ #
382
+ c = WebAgent::Cookie.new()
383
+ c.name = "hoge"
384
+ c.value = "funi"
385
+ #c.path = '' NO path given -> same as URL
386
+ c.url = urify("http://www.inac.co.jp/hoge/hoge2/hoge3")
387
+ @cm.add(c)
388
+ #
389
+ c1, c2 = @cm.cookies
390
+ assert_equal('', c1.path)
391
+ assert_equal('/hoge/hoge2', c2.path)
392
+ end
393
+
394
+ def test_check_cookie_accept_domain()
395
+ @cm.accept_domains = [".example1.co.jp", "www1.example.jp"]
396
+ @cm.reject_domains = [".example2.co.jp", "www2.example.jp"]
397
+ check1 = @cm.check_cookie_accept_domain("www.example1.co.jp")
398
+ assert_equal(true, check1)
399
+ check2 = @cm.check_cookie_accept_domain("www.example2.co.jp")
400
+ assert_equal(false, check2)
401
+ check3 = @cm.check_cookie_accept_domain("www1.example.jp")
402
+ assert_equal(true, check3)
403
+ check4 = @cm.check_cookie_accept_domain("www2.example.jp")
404
+ assert_equal(false, check4)
405
+ check5 = @cm.check_cookie_accept_domain("aa.www2.example.jp")
406
+ assert_equal(true, check5)
407
+ check6 = @cm.check_cookie_accept_domain("aa.www2.example.jp")
408
+ assert_equal(true, check6)
409
+ assert_equal(false, @cm.check_cookie_accept_domain(nil))
410
+ end
411
+
412
+ end
@@ -0,0 +1,14 @@
1
+ # -*- encoding: utf-8 -*-
2
+ require File.expand_path('helper', File.dirname(__FILE__))
3
+ require 'hexdump'
4
+
5
+
6
+ class TestHexDump < Test::Unit::TestCase
7
+ def test_encode
8
+ str = "\032l\277\370\2429\216\236\351[{\{\262\350\274\376"
9
+ str.force_encoding('BINARY') if str.respond_to?(:force_encoding)
10
+ assert_equal(["00000000 1a6cbff8 a2398e9e e95b7b7b b2e8bcfe .l...9...[{{...."], HexDump.encode(str))
11
+ end
12
+ end if defined?(RUBY_ENGINE) && RUBY_ENGINE != "rbx" && RUBY_VERSION >= "1.9.0"
13
+ # Rubinius 1.8 mode does not support Regexp.quote(raw, 'n') I don't want put
14
+ # a pressure on supporting it because 1.9 mode works fine.
@@ -0,0 +1,507 @@
1
+ require 'http-access2'
2
+ require File.expand_path('helper', File.dirname(__FILE__))
3
+
4
+
5
+ module HTTPAccess2
6
+
7
+
8
+ class TestClient < Test::Unit::TestCase
9
+ include Helper
10
+ include HTTPClient::Util
11
+
12
+ def setup
13
+ super
14
+ setup_server
15
+ setup_client
16
+ end
17
+
18
+ def teardown
19
+ super
20
+ end
21
+
22
+ def test_initialize
23
+ setup_proxyserver
24
+ escape_noproxy do
25
+ @proxyio.string = ""
26
+ @client = HTTPAccess2::Client.new(proxyurl)
27
+ assert_equal(urify(proxyurl), @client.proxy)
28
+ assert_equal(200, @client.head(serverurl).status)
29
+ assert(!@proxyio.string.empty?)
30
+ end
31
+ end
32
+
33
+ def test_agent_name
34
+ @client = HTTPAccess2::Client.new(nil, "agent_name_foo")
35
+ str = ""
36
+ @client.debug_dev = str
37
+ @client.get(serverurl)
38
+ lines = str.split(/(?:\r?\n)+/)
39
+ assert_equal("= Request", lines[0])
40
+ assert_match(/^User-Agent: agent_name_foo/, lines[4])
41
+ end
42
+
43
+ def test_from
44
+ @client = HTTPAccess2::Client.new(nil, nil, "from_bar")
45
+ str = ""
46
+ @client.debug_dev = str
47
+ @client.get(serverurl)
48
+ lines = str.split(/(?:\r?\n)+/)
49
+ assert_equal("= Request", lines[0])
50
+ assert_match(/^From: from_bar/, lines[5])
51
+ end
52
+
53
+ def test_debug_dev
54
+ str = ""
55
+ @client.debug_dev = str
56
+ assert(str.empty?)
57
+ @client.get(serverurl)
58
+ assert(!str.empty?)
59
+ end
60
+
61
+ def _test_protocol_version_http09
62
+ @client.protocol_version = 'HTTP/0.9'
63
+ str = ""
64
+ @client.debug_dev = str
65
+ @client.get(serverurl + 'hello')
66
+ lines = str.split(/(?:\r?\n)+/)
67
+ assert_equal("= Request", lines[0])
68
+ assert_equal("! CONNECTION ESTABLISHED", lines[2])
69
+ assert_equal("GET /hello HTTP/0.9", lines[3])
70
+ assert_equal("Connection: close", lines[5])
71
+ assert_equal("= Response", lines[6])
72
+ assert_match(/^hello/, lines[7])
73
+ end
74
+
75
+ def test_protocol_version_http10
76
+ @client.protocol_version = 'HTTP/1.0'
77
+ str = ""
78
+ @client.debug_dev = str
79
+ @client.get(serverurl + 'hello')
80
+ lines = str.split(/(?:\r?\n)+/)
81
+ assert_equal("= Request", lines[0])
82
+ assert_equal("! CONNECTION ESTABLISHED", lines[2])
83
+ assert_equal("GET /hello HTTP/1.0", lines[3])
84
+ assert_equal("Connection: close", lines[7])
85
+ assert_equal("= Response", lines[8])
86
+ end
87
+
88
+ def test_protocol_version_http11
89
+ str = ""
90
+ @client.debug_dev = str
91
+ @client.get(serverurl)
92
+ lines = str.split(/(?:\r?\n)+/)
93
+ assert_equal("= Request", lines[0])
94
+ assert_equal("! CONNECTION ESTABLISHED", lines[2])
95
+ assert_equal("GET / HTTP/1.1", lines[3])
96
+ assert_equal("Host: localhost:#{serverport}", lines[7])
97
+ @client.protocol_version = 'HTTP/1.1'
98
+ str = ""
99
+ @client.debug_dev = str
100
+ @client.get(serverurl)
101
+ lines = str.split(/(?:\r?\n)+/)
102
+ assert_equal("= Request", lines[0])
103
+ assert_equal("! CONNECTION ESTABLISHED", lines[2])
104
+ assert_equal("GET / HTTP/1.1", lines[3])
105
+ @client.protocol_version = 'HTTP/1.0'
106
+ str = ""
107
+ @client.debug_dev = str
108
+ @client.get(serverurl)
109
+ lines = str.split(/(?:\r?\n)+/)
110
+ assert_equal("= Request", lines[0])
111
+ assert_equal("! CONNECTION ESTABLISHED", lines[2])
112
+ assert_equal("GET / HTTP/1.0", lines[3])
113
+ end
114
+
115
+ def test_proxy
116
+ setup_proxyserver
117
+ escape_noproxy do
118
+ begin
119
+ @client.proxy = "http://"
120
+ rescue
121
+ assert_match(/InvalidURIError/, $!.class.to_s)
122
+ end
123
+ @client.proxy = ""
124
+ assert_nil(@client.proxy)
125
+ @client.proxy = "http://foo:1234"
126
+ assert_equal(urify("http://foo:1234"), @client.proxy)
127
+ uri = urify("http://bar:2345")
128
+ @client.proxy = uri
129
+ assert_equal(uri, @client.proxy)
130
+ #
131
+ @proxyio.string = ""
132
+ @client.proxy = nil
133
+ assert_equal(200, @client.head(serverurl).status)
134
+ assert(@proxyio.string.empty?)
135
+ #
136
+ @proxyio.string = ""
137
+ @client.proxy = proxyurl
138
+ assert_equal(200, @client.head(serverurl).status)
139
+ assert(!@proxyio.string.empty?)
140
+ end
141
+ end
142
+
143
+ def test_noproxy_for_localhost
144
+ @proxyio.string = ""
145
+ @client.proxy = proxyurl
146
+ assert_equal(200, @client.head(serverurl).status)
147
+ assert(@proxyio.string.empty?)
148
+ end
149
+
150
+ def test_no_proxy
151
+ setup_proxyserver
152
+ escape_noproxy do
153
+ # proxy is not set.
154
+ @client.no_proxy = 'localhost'
155
+ @proxyio.string = ""
156
+ @client.proxy = nil
157
+ assert_equal(200, @client.head(serverurl).status)
158
+ assert(/accept/ !~ @proxyio.string)
159
+ #
160
+ @proxyio.string = ""
161
+ @client.proxy = proxyurl
162
+ assert_equal(200, @client.head(serverurl).status)
163
+ assert(/accept/ !~ @proxyio.string)
164
+ #
165
+ @client.no_proxy = 'foobar'
166
+ @proxyio.string = ""
167
+ @client.proxy = proxyurl
168
+ assert_equal(200, @client.head(serverurl).status)
169
+ assert(/accept/ =~ @proxyio.string)
170
+ #
171
+ @client.no_proxy = 'foobar,localhost:baz'
172
+ @proxyio.string = ""
173
+ @client.proxy = proxyurl
174
+ assert_equal(200, @client.head(serverurl).status)
175
+ assert(/accept/ !~ @proxyio.string)
176
+ #
177
+ @client.no_proxy = 'foobar,localhost:443'
178
+ @proxyio.string = ""
179
+ @client.proxy = proxyurl
180
+ assert_equal(200, @client.head(serverurl).status)
181
+ assert(/accept/ =~ @proxyio.string)
182
+ #
183
+ @client.no_proxy = "foobar,localhost:443:localhost:#{serverport},baz"
184
+ @proxyio.string = ""
185
+ @client.proxy = proxyurl
186
+ assert_equal(200, @client.head(serverurl).status)
187
+ assert(/accept/ !~ @proxyio.string)
188
+ end
189
+ end
190
+
191
+ def test_get_content
192
+ assert_equal('hello', @client.get_content(serverurl + 'hello'))
193
+ assert_equal('hello', @client.get_content(serverurl + 'redirect1'))
194
+ assert_equal('hello', @client.get_content(serverurl + 'redirect2'))
195
+ assert_raises(HTTPClient::Session::BadResponse) do
196
+ @client.get_content(serverurl + 'notfound')
197
+ end
198
+ assert_raises(HTTPClient::Session::BadResponse) do
199
+ @client.get_content(serverurl + 'redirect_self')
200
+ end
201
+ called = false
202
+ @client.redirect_uri_callback = lambda { |uri, res|
203
+ newuri = res.header['location'][0]
204
+ called = true
205
+ newuri
206
+ }
207
+ assert_equal('hello', @client.get_content(serverurl + 'relative_redirect'))
208
+ assert(called)
209
+ end
210
+
211
+ def test_post_content
212
+ assert_equal('hello', @client.post_content(serverurl + 'hello'))
213
+ assert_equal('hello', @client.post_content(serverurl + 'redirect1'))
214
+ assert_equal('hello', @client.post_content(serverurl + 'redirect2'))
215
+ assert_raises(HTTPClient::Session::BadResponse) do
216
+ @client.post_content(serverurl + 'notfound')
217
+ end
218
+ assert_raises(HTTPClient::Session::BadResponse) do
219
+ @client.post_content(serverurl + 'redirect_self')
220
+ end
221
+ called = false
222
+ @client.redirect_uri_callback = lambda { |uri, res|
223
+ newuri = res.header['location'][0]
224
+ called = true
225
+ newuri
226
+ }
227
+ assert_equal('hello', @client.post_content(serverurl + 'relative_redirect'))
228
+ assert(called)
229
+ end
230
+
231
+ def test_head
232
+ assert_equal("head", @client.head(serverurl + 'servlet').header["x-head"][0])
233
+ param = {'1'=>'2', '3'=>'4'}
234
+ res = @client.head(serverurl + 'servlet', param)
235
+ assert_equal(param, params(res.header["x-query"][0]))
236
+ end
237
+
238
+ def test_get
239
+ assert_equal("get", @client.get(serverurl + 'servlet').content)
240
+ param = {'1'=>'2', '3'=>'4'}
241
+ res = @client.get(serverurl + 'servlet', param)
242
+ assert_equal(param, params(res.header["x-query"][0]))
243
+ end
244
+
245
+ def test_post
246
+ assert_equal("post", @client.post(serverurl + 'servlet').content)
247
+ param = {'1'=>'2', '3'=>'4'}
248
+ res = @client.get(serverurl + 'servlet', param)
249
+ assert_equal(param, params(res.header["x-query"][0]))
250
+ end
251
+
252
+ def test_put
253
+ assert_equal("put", @client.put(serverurl + 'servlet').content)
254
+ param = {'1'=>'2', '3'=>'4'}
255
+ res = @client.get(serverurl + 'servlet', param)
256
+ assert_equal(param, params(res.header["x-query"][0]))
257
+ end
258
+
259
+ def test_delete
260
+ assert_equal("delete", @client.delete(serverurl + 'servlet').content)
261
+ param = {'1'=>'2', '3'=>'4'}
262
+ res = @client.get(serverurl + 'servlet', param)
263
+ assert_equal(param, params(res.header["x-query"][0]))
264
+ end
265
+
266
+ def test_options
267
+ assert_equal("options", @client.options(serverurl + 'servlet').content)
268
+ param = {'1'=>'2', '3'=>'4'}
269
+ res = @client.get(serverurl + 'servlet', param)
270
+ assert_equal(param, params(res.header["x-query"][0]))
271
+ end
272
+
273
+ def test_trace
274
+ assert_equal("trace", @client.trace(serverurl + 'servlet').content)
275
+ param = {'1'=>'2', '3'=>'4'}
276
+ res = @client.get(serverurl + 'servlet', param)
277
+ assert_equal(param, params(res.header["x-query"][0]))
278
+ end
279
+
280
+ def test_get_query
281
+ assert_equal({'1'=>'2'}, check_query_get({1=>2}))
282
+ assert_equal({'a'=>'A', 'B'=>'b'}, check_query_get({"a"=>"A", "B"=>"b"}))
283
+ assert_equal({'&'=>'&'}, check_query_get({"&"=>"&"}))
284
+ assert_equal({'= '=>' =+'}, check_query_get({"= "=>" =+"}))
285
+ assert_equal(
286
+ ['=', '&'].sort,
287
+ check_query_get([["=", "="], ["=", "&"]])['='].to_ary.sort
288
+ )
289
+ assert_equal({'123'=>'45'}, check_query_get('123=45'))
290
+ assert_equal({'12 3'=>'45', ' '=>' '}, check_query_get('12+3=45&+=+'))
291
+ assert_equal({}, check_query_get(''))
292
+ end
293
+
294
+ def test_post_body
295
+ assert_equal({'1'=>'2'}, check_query_post({1=>2}))
296
+ assert_equal({'a'=>'A', 'B'=>'b'}, check_query_post({"a"=>"A", "B"=>"b"}))
297
+ assert_equal({'&'=>'&'}, check_query_post({"&"=>"&"}))
298
+ assert_equal({'= '=>' =+'}, check_query_post({"= "=>" =+"}))
299
+ assert_equal(
300
+ ['=', '&'].sort,
301
+ check_query_post([["=", "="], ["=", "&"]])['='].to_ary.sort
302
+ )
303
+ assert_equal({'123'=>'45'}, check_query_post('123=45'))
304
+ assert_equal({'12 3'=>'45', ' '=>' '}, check_query_post('12+3=45&+=+'))
305
+ assert_equal({}, check_query_post(''))
306
+ #
307
+ post_body = StringIO.new("foo=bar&foo=baz")
308
+ assert_equal(
309
+ ["bar", "baz"],
310
+ check_query_post(post_body)["foo"].to_ary.sort
311
+ )
312
+ end
313
+
314
+ def test_extra_headers
315
+ str = ""
316
+ @client.debug_dev = str
317
+ @client.head(serverurl, nil, {"ABC" => "DEF"})
318
+ lines = str.split(/(?:\r?\n)+/)
319
+ assert_equal("= Request", lines[0])
320
+ assert_match("ABC: DEF", lines[4])
321
+ #
322
+ str = ""
323
+ @client.debug_dev = str
324
+ @client.get(serverurl, nil, [["ABC", "DEF"], ["ABC", "DEF"]])
325
+ lines = str.split(/(?:\r?\n)+/)
326
+ assert_equal("= Request", lines[0])
327
+ assert_match("ABC: DEF", lines[4])
328
+ assert_match("ABC: DEF", lines[5])
329
+ end
330
+
331
+ def test_timeout
332
+ assert_equal(60, @client.connect_timeout)
333
+ assert_equal(120, @client.send_timeout)
334
+ assert_equal(60, @client.receive_timeout)
335
+ end
336
+
337
+ def test_connect_timeout
338
+ # ToDo
339
+ end
340
+
341
+ def test_send_timeout
342
+ # ToDo
343
+ end
344
+
345
+ def test_receive_timeout
346
+ # this test takes 2 sec
347
+ assert_equal('hello', @client.get_content(serverurl + 'sleep?sec=2'))
348
+ @client.receive_timeout = 1
349
+ assert_equal('hello', @client.get_content(serverurl + 'sleep?sec=0'))
350
+ assert_raise(HTTPClient::ReceiveTimeoutError) do
351
+ @client.get_content(serverurl + 'sleep?sec=2')
352
+ end
353
+ @client.receive_timeout = 3
354
+ assert_equal('hello', @client.get_content(serverurl + 'sleep?sec=2'))
355
+ end
356
+
357
+ def test_cookies
358
+ cookiefile = File.join(File.dirname(File.expand_path(__FILE__)),
359
+ 'test_cookies_file')
360
+ # from [ruby-talk:164079]
361
+ File.open(cookiefile, "wb") do |f|
362
+ f << "http://rubyforge.org//account/login.php session_ser LjEwMy45Ni40Ni0q%2A-fa0537de8cc31 1131676286 .rubyforge.org / 13\n"
363
+ end
364
+ cm = WebAgent::CookieManager::new(cookiefile)
365
+ cm.load_cookies
366
+ cookie = cm.cookies.first
367
+ url = cookie.url
368
+ assert(cookie.domain_match(url.host, cookie.domain))
369
+ end
370
+
371
+ private
372
+
373
+ def check_query_get(query)
374
+ WEBrick::HTTPUtils.parse_query(
375
+ @client.get(serverurl + 'servlet', query).header["x-query"][0]
376
+ )
377
+ end
378
+
379
+ def check_query_post(query)
380
+ WEBrick::HTTPUtils.parse_query(
381
+ @client.post(serverurl + 'servlet', query).header["x-query"][0]
382
+ )
383
+ end
384
+
385
+ def setup_server
386
+ @server = WEBrick::HTTPServer.new(
387
+ :BindAddress => "localhost",
388
+ :Logger => @logger,
389
+ :Port => 0,
390
+ :AccessLog => [],
391
+ :DocumentRoot => File.dirname(File.expand_path(__FILE__))
392
+ )
393
+ @serverport = @server.config[:Port]
394
+ [:hello, :sleep, :redirect1, :redirect2, :redirect3, :redirect_self, :relative_redirect].each do |sym|
395
+ @server.mount(
396
+ "/#{sym}",
397
+ WEBrick::HTTPServlet::ProcHandler.new(method("do_#{sym}").to_proc)
398
+ )
399
+ end
400
+ @server.mount('/servlet', TestServlet.new(@server))
401
+ @server_thread = start_server_thread(@server)
402
+ end
403
+
404
+ def escape_noproxy
405
+ backup = HTTPAccess2::Client::NO_PROXY_HOSTS.dup
406
+ HTTPAccess2::Client::NO_PROXY_HOSTS.clear
407
+ yield
408
+ ensure
409
+ HTTPAccess2::Client::NO_PROXY_HOSTS.replace(backup)
410
+ end
411
+
412
+ def do_hello(req, res)
413
+ res['content-type'] = 'text/html'
414
+ res.body = "hello"
415
+ end
416
+
417
+ def do_sleep(req, res)
418
+ sec = req.query['sec'].to_i
419
+ sleep sec
420
+ res['content-type'] = 'text/html'
421
+ res.body = "hello"
422
+ end
423
+
424
+ def do_redirect1(req, res)
425
+ res.set_redirect(WEBrick::HTTPStatus::MovedPermanently, serverurl + "hello")
426
+ end
427
+
428
+ def do_redirect2(req, res)
429
+ res.set_redirect(WEBrick::HTTPStatus::TemporaryRedirect, serverurl + "redirect3")
430
+ end
431
+
432
+ def do_redirect3(req, res)
433
+ res.set_redirect(WEBrick::HTTPStatus::Found, serverurl + "hello")
434
+ end
435
+
436
+ def do_redirect_self(req, res)
437
+ res.set_redirect(WEBrick::HTTPStatus::Found, serverurl + "redirect_self")
438
+ end
439
+
440
+ def do_relative_redirect(req, res)
441
+ res.set_redirect(WEBrick::HTTPStatus::Found, "hello")
442
+ end
443
+
444
+ class TestServlet < WEBrick::HTTPServlet::AbstractServlet
445
+ def get_instance(*arg)
446
+ self
447
+ end
448
+
449
+ def do_HEAD(req, res)
450
+ res["x-head"] = 'head' # use this for test purpose only.
451
+ res["x-query"] = query_response(req)
452
+ end
453
+
454
+ def do_GET(req, res)
455
+ res.body = 'get'
456
+ res["x-query"] = query_response(req)
457
+ end
458
+
459
+ def do_POST(req, res)
460
+ res.body = 'post'
461
+ res["x-query"] = body_response(req)
462
+ end
463
+
464
+ def do_PUT(req, res)
465
+ res.body = 'put'
466
+ end
467
+
468
+ def do_DELETE(req, res)
469
+ res.body = 'delete'
470
+ end
471
+
472
+ def do_OPTIONS(req, res)
473
+ # check RFC for legal response.
474
+ res.body = 'options'
475
+ end
476
+
477
+ def do_TRACE(req, res)
478
+ # client SHOULD reflect the message received back to the client as the
479
+ # entity-body of a 200 (OK) response. [RFC2616]
480
+ res.body = 'trace'
481
+ res["x-query"] = query_response(req)
482
+ end
483
+
484
+ private
485
+
486
+ def query_response(req)
487
+ query_escape(WEBrick::HTTPUtils.parse_query(req.query_string))
488
+ end
489
+
490
+ def body_response(req)
491
+ query_escape(WEBrick::HTTPUtils.parse_query(req.body))
492
+ end
493
+
494
+ def query_escape(query)
495
+ escaped = []
496
+ query.collect do |k, v|
497
+ v.to_ary.each do |ve|
498
+ escaped << CGI.escape(k) + '=' + CGI.escape(ve)
499
+ end
500
+ end
501
+ escaped.join('&')
502
+ end
503
+ end
504
+ end
505
+
506
+
507
+ end