scout 5.7.1 → 5.7.2.pre

Sign up to get free protection for your applications and to get access to all the features.
Files changed (251) hide show
  1. data/CHANGELOG.markdown +5 -0
  2. data/lib/scout/command/run.rb +1 -1
  3. data/lib/scout/server.rb +2 -1
  4. data/lib/scout/streamer.rb +3 -2
  5. data/lib/scout/streamer_daemon.rb +4 -4
  6. data/lib/scout/version.rb +1 -1
  7. data/test/scout_test.rb +7 -8
  8. data/vendor/httpclient/README.txt +759 -0
  9. data/vendor/httpclient/bin/httpclient +65 -0
  10. data/vendor/httpclient/lib/hexdump.rb +50 -0
  11. data/vendor/httpclient/lib/http-access2.rb +55 -0
  12. data/vendor/httpclient/lib/http-access2/cookie.rb +1 -0
  13. data/vendor/httpclient/lib/http-access2/http.rb +1 -0
  14. data/vendor/httpclient/lib/httpclient.rb +1156 -0
  15. data/vendor/httpclient/lib/httpclient/auth.rb +899 -0
  16. data/vendor/httpclient/lib/httpclient/cacert.p7s +1912 -0
  17. data/vendor/httpclient/lib/httpclient/connection.rb +88 -0
  18. data/vendor/httpclient/lib/httpclient/cookie.rb +438 -0
  19. data/vendor/httpclient/lib/httpclient/http.rb +1046 -0
  20. data/vendor/httpclient/lib/httpclient/include_client.rb +83 -0
  21. data/vendor/httpclient/lib/httpclient/session.rb +1025 -0
  22. data/vendor/httpclient/lib/httpclient/ssl_config.rb +403 -0
  23. data/vendor/httpclient/lib/httpclient/timeout.rb +140 -0
  24. data/vendor/httpclient/lib/httpclient/util.rb +178 -0
  25. data/vendor/httpclient/lib/httpclient/version.rb +3 -0
  26. data/vendor/httpclient/lib/oauthclient.rb +110 -0
  27. data/vendor/httpclient/sample/async.rb +8 -0
  28. data/vendor/httpclient/sample/auth.rb +11 -0
  29. data/vendor/httpclient/sample/cookie.rb +18 -0
  30. data/vendor/httpclient/sample/dav.rb +103 -0
  31. data/vendor/httpclient/sample/howto.rb +49 -0
  32. data/vendor/httpclient/sample/oauth_buzz.rb +57 -0
  33. data/vendor/httpclient/sample/oauth_friendfeed.rb +59 -0
  34. data/vendor/httpclient/sample/oauth_salesforce_10.rb +63 -0
  35. data/vendor/httpclient/sample/oauth_twitter.rb +61 -0
  36. data/vendor/httpclient/sample/ssl/0cert.pem +22 -0
  37. data/vendor/httpclient/sample/ssl/0key.pem +30 -0
  38. data/vendor/httpclient/sample/ssl/1000cert.pem +19 -0
  39. data/vendor/httpclient/sample/ssl/1000key.pem +18 -0
  40. data/vendor/httpclient/sample/ssl/htdocs/index.html +10 -0
  41. data/vendor/httpclient/sample/ssl/ssl_client.rb +22 -0
  42. data/vendor/httpclient/sample/ssl/webrick_httpsd.rb +29 -0
  43. data/vendor/httpclient/sample/stream.rb +21 -0
  44. data/vendor/httpclient/sample/thread.rb +27 -0
  45. data/vendor/httpclient/sample/wcat.rb +21 -0
  46. data/vendor/httpclient/test/ca-chain.cert +44 -0
  47. data/vendor/httpclient/test/ca.cert +23 -0
  48. data/vendor/httpclient/test/client.cert +19 -0
  49. data/vendor/httpclient/test/client.key +15 -0
  50. data/vendor/httpclient/test/helper.rb +129 -0
  51. data/vendor/httpclient/test/htdigest +1 -0
  52. data/vendor/httpclient/test/htpasswd +2 -0
  53. data/vendor/httpclient/test/runner.rb +2 -0
  54. data/vendor/httpclient/test/server.cert +19 -0
  55. data/vendor/httpclient/test/server.key +15 -0
  56. data/vendor/httpclient/test/sslsvr.rb +65 -0
  57. data/vendor/httpclient/test/subca.cert +21 -0
  58. data/vendor/httpclient/test/test_auth.rb +321 -0
  59. data/vendor/httpclient/test/test_cookie.rb +391 -0
  60. data/vendor/httpclient/test/test_hexdump.rb +14 -0
  61. data/vendor/httpclient/test/test_http-access2.rb +507 -0
  62. data/vendor/httpclient/test/test_httpclient.rb +1783 -0
  63. data/vendor/httpclient/test/test_include_client.rb +52 -0
  64. data/vendor/httpclient/test/test_ssl.rb +235 -0
  65. data/vendor/multi_json/.document +5 -0
  66. data/vendor/multi_json/.rspec +3 -0
  67. data/vendor/multi_json/.travis.yml +11 -0
  68. data/vendor/multi_json/.yardopts +6 -0
  69. data/vendor/multi_json/CHANGELOG.md +169 -0
  70. data/vendor/multi_json/CONTRIBUTING.md +46 -0
  71. data/vendor/multi_json/Gemfile +31 -0
  72. data/vendor/multi_json/LICENSE.md +20 -0
  73. data/vendor/multi_json/README.md +109 -0
  74. data/vendor/multi_json/Rakefile +12 -0
  75. data/vendor/multi_json/lib/multi_json.rb +157 -0
  76. data/vendor/multi_json/lib/multi_json/adapter.rb +48 -0
  77. data/vendor/multi_json/lib/multi_json/adapters/gson.rb +19 -0
  78. data/vendor/multi_json/lib/multi_json/adapters/jr_jackson.rb +19 -0
  79. data/vendor/multi_json/lib/multi_json/adapters/json_common.rb +25 -0
  80. data/vendor/multi_json/lib/multi_json/adapters/json_gem.rb +11 -0
  81. data/vendor/multi_json/lib/multi_json/adapters/json_pure.rb +11 -0
  82. data/vendor/multi_json/lib/multi_json/adapters/nsjsonserialization.rb +34 -0
  83. data/vendor/multi_json/lib/multi_json/adapters/oj.rb +24 -0
  84. data/vendor/multi_json/lib/multi_json/adapters/ok_json.rb +22 -0
  85. data/vendor/multi_json/lib/multi_json/adapters/yajl.rb +19 -0
  86. data/vendor/multi_json/lib/multi_json/convertible_hash_keys.rb +43 -0
  87. data/vendor/multi_json/lib/multi_json/load_error.rb +11 -0
  88. data/vendor/multi_json/lib/multi_json/options.rb +48 -0
  89. data/vendor/multi_json/lib/multi_json/vendor/okjson.rb +606 -0
  90. data/vendor/multi_json/lib/multi_json/version.rb +20 -0
  91. data/vendor/multi_json/multi_json.gemspec +22 -0
  92. data/vendor/multi_json/spec/adapter_shared_example.rb +235 -0
  93. data/vendor/multi_json/spec/has_options.rb +119 -0
  94. data/vendor/multi_json/spec/helper.rb +35 -0
  95. data/vendor/multi_json/spec/json_common_shared_example.rb +30 -0
  96. data/vendor/multi_json/spec/multi_json_spec.rb +226 -0
  97. data/vendor/{signature → pusher}/.document +0 -0
  98. data/vendor/{json_pure/diagrams/.keep → pusher/.gemtest} +0 -0
  99. data/vendor/pusher/.gitignore +23 -0
  100. data/vendor/pusher/.travis.yml +15 -0
  101. data/vendor/pusher/Gemfile +2 -0
  102. data/vendor/{pusher-gem → pusher}/LICENSE +1 -1
  103. data/vendor/pusher/README.md +186 -0
  104. data/vendor/{pusher-gem → pusher}/Rakefile +0 -0
  105. data/vendor/{pusher-gem → pusher}/examples/async_message.rb +0 -0
  106. data/vendor/pusher/lib/pusher.rb +60 -0
  107. data/vendor/{pusher-gem → pusher}/lib/pusher/channel.rb +47 -54
  108. data/vendor/pusher/lib/pusher/client.rb +306 -0
  109. data/vendor/pusher/lib/pusher/request.rb +107 -0
  110. data/vendor/pusher/lib/pusher/resource.rb +36 -0
  111. data/vendor/pusher/lib/pusher/webhook.rb +110 -0
  112. data/vendor/{pusher-gem → pusher}/pusher.gemspec +6 -5
  113. data/vendor/pusher/spec/channel_spec.rb +127 -0
  114. data/vendor/pusher/spec/client_spec.rb +464 -0
  115. data/vendor/{pusher-gem → pusher}/spec/spec_helper.rb +12 -0
  116. data/vendor/pusher/spec/web_hook_spec.rb +117 -0
  117. data/vendor/signature/.travis.yml +15 -0
  118. data/vendor/signature/Gemfile +1 -1
  119. data/vendor/signature/README.md +38 -28
  120. data/vendor/signature/lib/signature.rb +97 -15
  121. data/vendor/signature/lib/signature/query_encoder.rb +47 -0
  122. data/vendor/signature/lib/signature/version.rb +1 -1
  123. data/vendor/signature/signature.gemspec +3 -2
  124. data/vendor/signature/spec/signature_spec.rb +164 -55
  125. data/vendor/signature/spec/spec_helper.rb +2 -3
  126. metadata +120 -145
  127. data/vendor/json_pure/.gitignore +0 -12
  128. data/vendor/json_pure/.travis.yml +0 -20
  129. data/vendor/json_pure/CHANGES +0 -282
  130. data/vendor/json_pure/COPYING +0 -58
  131. data/vendor/json_pure/COPYING-json-jruby +0 -57
  132. data/vendor/json_pure/GPL +0 -340
  133. data/vendor/json_pure/Gemfile +0 -11
  134. data/vendor/json_pure/README-json-jruby.markdown +0 -33
  135. data/vendor/json_pure/README.rdoc +0 -358
  136. data/vendor/json_pure/Rakefile +0 -412
  137. data/vendor/json_pure/TODO +0 -1
  138. data/vendor/json_pure/VERSION +0 -1
  139. data/vendor/json_pure/data/example.json +0 -1
  140. data/vendor/json_pure/data/index.html +0 -38
  141. data/vendor/json_pure/data/prototype.js +0 -4184
  142. data/vendor/json_pure/ext/json/ext/fbuffer/fbuffer.h +0 -181
  143. data/vendor/json_pure/ext/json/ext/generator/depend +0 -1
  144. data/vendor/json_pure/ext/json/ext/generator/extconf.rb +0 -14
  145. data/vendor/json_pure/ext/json/ext/generator/generator.c +0 -1435
  146. data/vendor/json_pure/ext/json/ext/generator/generator.h +0 -148
  147. data/vendor/json_pure/ext/json/ext/parser/depend +0 -1
  148. data/vendor/json_pure/ext/json/ext/parser/extconf.rb +0 -13
  149. data/vendor/json_pure/ext/json/ext/parser/parser.c +0 -2204
  150. data/vendor/json_pure/ext/json/ext/parser/parser.h +0 -77
  151. data/vendor/json_pure/ext/json/ext/parser/parser.rl +0 -927
  152. data/vendor/json_pure/install.rb +0 -23
  153. data/vendor/json_pure/java/src/json/ext/ByteListTranscoder.java +0 -167
  154. data/vendor/json_pure/java/src/json/ext/Generator.java +0 -444
  155. data/vendor/json_pure/java/src/json/ext/GeneratorMethods.java +0 -232
  156. data/vendor/json_pure/java/src/json/ext/GeneratorService.java +0 -43
  157. data/vendor/json_pure/java/src/json/ext/GeneratorState.java +0 -543
  158. data/vendor/json_pure/java/src/json/ext/OptionsReader.java +0 -114
  159. data/vendor/json_pure/java/src/json/ext/Parser.java +0 -2644
  160. data/vendor/json_pure/java/src/json/ext/Parser.rl +0 -968
  161. data/vendor/json_pure/java/src/json/ext/ParserService.java +0 -35
  162. data/vendor/json_pure/java/src/json/ext/RuntimeInfo.java +0 -121
  163. data/vendor/json_pure/java/src/json/ext/StringDecoder.java +0 -167
  164. data/vendor/json_pure/java/src/json/ext/StringEncoder.java +0 -106
  165. data/vendor/json_pure/java/src/json/ext/Utils.java +0 -89
  166. data/vendor/json_pure/json-java.gemspec +0 -23
  167. data/vendor/json_pure/json.gemspec +0 -37
  168. data/vendor/json_pure/json_pure.gemspec +0 -39
  169. data/vendor/json_pure/lib/json.rb +0 -62
  170. data/vendor/json_pure/lib/json/add/bigdecimal.rb +0 -28
  171. data/vendor/json_pure/lib/json/add/complex.rb +0 -22
  172. data/vendor/json_pure/lib/json/add/core.rb +0 -11
  173. data/vendor/json_pure/lib/json/add/date.rb +0 -34
  174. data/vendor/json_pure/lib/json/add/date_time.rb +0 -50
  175. data/vendor/json_pure/lib/json/add/exception.rb +0 -31
  176. data/vendor/json_pure/lib/json/add/ostruct.rb +0 -31
  177. data/vendor/json_pure/lib/json/add/range.rb +0 -29
  178. data/vendor/json_pure/lib/json/add/rational.rb +0 -22
  179. data/vendor/json_pure/lib/json/add/regexp.rb +0 -30
  180. data/vendor/json_pure/lib/json/add/struct.rb +0 -30
  181. data/vendor/json_pure/lib/json/add/symbol.rb +0 -25
  182. data/vendor/json_pure/lib/json/add/time.rb +0 -38
  183. data/vendor/json_pure/lib/json/common.rb +0 -487
  184. data/vendor/json_pure/lib/json/ext.rb +0 -21
  185. data/vendor/json_pure/lib/json/ext/.keep +0 -0
  186. data/vendor/json_pure/lib/json/generic_object.rb +0 -70
  187. data/vendor/json_pure/lib/json/pure.rb +0 -21
  188. data/vendor/json_pure/lib/json/pure/generator.rb +0 -522
  189. data/vendor/json_pure/lib/json/pure/parser.rb +0 -359
  190. data/vendor/json_pure/lib/json/version.rb +0 -8
  191. data/vendor/json_pure/tests/fixtures/fail1.json +0 -1
  192. data/vendor/json_pure/tests/fixtures/fail10.json +0 -1
  193. data/vendor/json_pure/tests/fixtures/fail11.json +0 -1
  194. data/vendor/json_pure/tests/fixtures/fail12.json +0 -1
  195. data/vendor/json_pure/tests/fixtures/fail13.json +0 -1
  196. data/vendor/json_pure/tests/fixtures/fail14.json +0 -1
  197. data/vendor/json_pure/tests/fixtures/fail18.json +0 -1
  198. data/vendor/json_pure/tests/fixtures/fail19.json +0 -1
  199. data/vendor/json_pure/tests/fixtures/fail2.json +0 -1
  200. data/vendor/json_pure/tests/fixtures/fail20.json +0 -1
  201. data/vendor/json_pure/tests/fixtures/fail21.json +0 -1
  202. data/vendor/json_pure/tests/fixtures/fail22.json +0 -1
  203. data/vendor/json_pure/tests/fixtures/fail23.json +0 -1
  204. data/vendor/json_pure/tests/fixtures/fail24.json +0 -1
  205. data/vendor/json_pure/tests/fixtures/fail25.json +0 -1
  206. data/vendor/json_pure/tests/fixtures/fail27.json +0 -2
  207. data/vendor/json_pure/tests/fixtures/fail28.json +0 -2
  208. data/vendor/json_pure/tests/fixtures/fail3.json +0 -1
  209. data/vendor/json_pure/tests/fixtures/fail4.json +0 -1
  210. data/vendor/json_pure/tests/fixtures/fail5.json +0 -1
  211. data/vendor/json_pure/tests/fixtures/fail6.json +0 -1
  212. data/vendor/json_pure/tests/fixtures/fail7.json +0 -1
  213. data/vendor/json_pure/tests/fixtures/fail8.json +0 -1
  214. data/vendor/json_pure/tests/fixtures/fail9.json +0 -1
  215. data/vendor/json_pure/tests/fixtures/pass1.json +0 -56
  216. data/vendor/json_pure/tests/fixtures/pass15.json +0 -1
  217. data/vendor/json_pure/tests/fixtures/pass16.json +0 -1
  218. data/vendor/json_pure/tests/fixtures/pass17.json +0 -1
  219. data/vendor/json_pure/tests/fixtures/pass2.json +0 -1
  220. data/vendor/json_pure/tests/fixtures/pass26.json +0 -1
  221. data/vendor/json_pure/tests/fixtures/pass3.json +0 -6
  222. data/vendor/json_pure/tests/setup_variant.rb +0 -11
  223. data/vendor/json_pure/tests/test_json.rb +0 -545
  224. data/vendor/json_pure/tests/test_json_addition.rb +0 -196
  225. data/vendor/json_pure/tests/test_json_encoding.rb +0 -65
  226. data/vendor/json_pure/tests/test_json_fixtures.rb +0 -35
  227. data/vendor/json_pure/tests/test_json_generate.rb +0 -322
  228. data/vendor/json_pure/tests/test_json_generic_object.rb +0 -75
  229. data/vendor/json_pure/tests/test_json_string_matching.rb +0 -39
  230. data/vendor/json_pure/tests/test_json_unicode.rb +0 -72
  231. data/vendor/json_pure/tools/fuzz.rb +0 -139
  232. data/vendor/json_pure/tools/server.rb +0 -62
  233. data/vendor/pusher-gem/Gemfile +0 -2
  234. data/vendor/pusher-gem/README.md +0 -80
  235. data/vendor/pusher-gem/lib/pusher.rb +0 -107
  236. data/vendor/pusher-gem/lib/pusher/request.rb +0 -107
  237. data/vendor/pusher-gem/spec/channel_spec.rb +0 -274
  238. data/vendor/pusher-gem/spec/pusher_spec.rb +0 -87
  239. data/vendor/ruby-hmac/History.txt +0 -15
  240. data/vendor/ruby-hmac/Manifest.txt +0 -11
  241. data/vendor/ruby-hmac/README.md +0 -41
  242. data/vendor/ruby-hmac/Rakefile +0 -23
  243. data/vendor/ruby-hmac/lib/hmac-md5.rb +0 -11
  244. data/vendor/ruby-hmac/lib/hmac-rmd160.rb +0 -11
  245. data/vendor/ruby-hmac/lib/hmac-sha1.rb +0 -11
  246. data/vendor/ruby-hmac/lib/hmac-sha2.rb +0 -25
  247. data/vendor/ruby-hmac/lib/hmac.rb +0 -118
  248. data/vendor/ruby-hmac/lib/ruby_hmac.rb +0 -2
  249. data/vendor/ruby-hmac/ruby-hmac.gemspec +0 -33
  250. data/vendor/ruby-hmac/test/test_hmac.rb +0 -89
  251. data/vendor/signature/VERSION +0 -1
@@ -0,0 +1,88 @@
1
+ # HTTPClient - HTTP client library.
2
+ # Copyright (C) 2000-2009 NAKAMURA, Hiroshi <nahi@ruby-lang.org>.
3
+ #
4
+ # This program is copyrighted free software by NAKAMURA, Hiroshi. You can
5
+ # redistribute it and/or modify it under the same terms of Ruby's license;
6
+ # either the dual license version in 2003, or any later version.
7
+
8
+
9
+ class HTTPClient
10
+
11
+
12
+ # Represents a HTTP response to an asynchronous request. Async methods of
13
+ # HTTPClient such as get_async, post_async, etc. returns an instance of
14
+ # Connection.
15
+ #
16
+ # == How to use
17
+ #
18
+ # 1. Invoke HTTP method asynchronously and check if it's been finished
19
+ # periodically.
20
+ #
21
+ # connection = clnt.post_async(url, body)
22
+ # print 'posting.'
23
+ # while true
24
+ # break if connection.finished?
25
+ # print '.'
26
+ # sleep 1
27
+ # end
28
+ # puts '.'
29
+ # res = connection.pop
30
+ # p res.status
31
+ #
32
+ # 2. Read the response as an IO.
33
+ #
34
+ # connection = clnt.get_async('http://dev.ctor.org/')
35
+ # io = connection.pop.content
36
+ # while str = io.read(40)
37
+ # p str
38
+ # end
39
+ class Connection
40
+ attr_accessor :async_thread
41
+
42
+ def initialize(header_queue = [], body_queue = []) # :nodoc:
43
+ @headers = header_queue
44
+ @body = body_queue
45
+ @async_thread = nil
46
+ @queue = Queue.new
47
+ end
48
+
49
+ # Checks if the asynchronous invocation has been finished or not.
50
+ def finished?
51
+ if !@async_thread
52
+ # Not in async mode.
53
+ true
54
+ elsif @async_thread.alive?
55
+ # Working...
56
+ false
57
+ else
58
+ # Async thread have been finished.
59
+ join
60
+ true
61
+ end
62
+ end
63
+
64
+ # Retrieves a HTTP::Message instance of HTTP response. Do not invoke this
65
+ # method twice for now. The second invocation will be blocked.
66
+ def pop
67
+ response_or_exception = @queue.pop
68
+ if response_or_exception.is_a? Exception
69
+ raise response_or_exception
70
+ end
71
+ response_or_exception
72
+ end
73
+
74
+ def push(result) # :nodoc:
75
+ @queue.push(result)
76
+ end
77
+
78
+ # Waits the completion of the asynchronous invocation.
79
+ def join
80
+ if @async_thread
81
+ @async_thread.join
82
+ end
83
+ nil
84
+ end
85
+ end
86
+
87
+
88
+ end
@@ -0,0 +1,438 @@
1
+ # cookie.rb is redistributed file which is originally included in Webagent
2
+ # version 0.6.2 by TAKAHASHI `Maki' Masayoshi. And it contains some bug fixes.
3
+ # You can download the entire package of Webagent from
4
+ # http://www.rubycolor.org/arc/.
5
+
6
+
7
+ # Cookie class
8
+ #
9
+ # I refered to w3m's source to make these classes. Some comments
10
+ # are quoted from it. I'm thanksful for author(s) of it.
11
+ #
12
+ # w3m homepage: http://ei5nazha.yz.yamagata-u.ac.jp/~aito/w3m/eng/
13
+
14
+ require 'time'
15
+ require 'monitor'
16
+ require 'httpclient/util'
17
+
18
+ class WebAgent
19
+
20
+ module CookieUtils
21
+
22
+ def head_match?(str1, str2)
23
+ str1 == str2[0, str1.length]
24
+ end
25
+
26
+ def tail_match?(str1, str2)
27
+ if str1.length > 0
28
+ str1 == str2[-str1.length..-1].to_s
29
+ else
30
+ true
31
+ end
32
+ end
33
+
34
+ def domain_match(host, domain)
35
+ domainname = domain.sub(/\.\z/, '').downcase
36
+ hostname = host.sub(/\.\z/, '').downcase
37
+ case domain
38
+ when /\d+\.\d+\.\d+\.\d+/
39
+ return (hostname == domainname)
40
+ when '.'
41
+ return true
42
+ when /^\./
43
+ # allows; host == rubyforge.org, domain == .rubyforge.org
44
+ return tail_match?(domainname, '.' + hostname)
45
+ else
46
+ return (hostname == domainname)
47
+ end
48
+ end
49
+ end
50
+
51
+ class Cookie
52
+ include CookieUtils
53
+
54
+ attr_accessor :name, :value
55
+ attr_accessor :domain, :path
56
+ attr_accessor :expires ## for Netscape Cookie
57
+ attr_accessor :url
58
+ attr_writer :use, :secure, :http_only, :discard, :domain_orig, :path_orig, :override
59
+
60
+ USE = 1
61
+ SECURE = 2
62
+ DOMAIN = 4
63
+ PATH = 8
64
+ DISCARD = 16
65
+ OVERRIDE = 32
66
+ OVERRIDE_OK = 32
67
+ HTTP_ONLY = 64
68
+
69
+ def initialize
70
+ @name = @value = @domain = @path = nil
71
+ @expires = nil
72
+ @url = nil
73
+ @use = @secure = @http_only = @discard = @domain_orig = @path_orig = @override = nil
74
+ end
75
+
76
+ def discard?
77
+ @discard
78
+ end
79
+
80
+ def use?
81
+ @use
82
+ end
83
+
84
+ def secure?
85
+ @secure
86
+ end
87
+
88
+ def http_only?
89
+ @http_only
90
+ end
91
+
92
+ def domain_orig?
93
+ @domain_orig
94
+ end
95
+
96
+ def path_orig?
97
+ @path_orig
98
+ end
99
+
100
+ def override?
101
+ @override
102
+ end
103
+
104
+ def flag
105
+ flg = 0
106
+ flg += USE if @use
107
+ flg += SECURE if @secure
108
+ flg += HTTP_ONLY if @http_only
109
+ flg += DOMAIN if @domain_orig
110
+ flg += PATH if @path_orig
111
+ flg += DISCARD if @discard
112
+ flg += OVERRIDE if @override
113
+ flg
114
+ end
115
+
116
+ def set_flag(flag)
117
+ flag = flag.to_i
118
+ @use = true if flag & USE > 0
119
+ @secure = true if flag & SECURE > 0
120
+ @http_only = true if flag & HTTP_ONLY > 0
121
+ @domain_orig = true if flag & DOMAIN > 0
122
+ @path_orig = true if flag & PATH > 0
123
+ @discard = true if flag & DISCARD > 0
124
+ @override = true if flag & OVERRIDE > 0
125
+ end
126
+
127
+ def match?(url)
128
+ domainname = url.host
129
+ if (!domainname ||
130
+ !domain_match(domainname, @domain) ||
131
+ (@path && !head_match?(@path, url.path.empty? ? '/' : url.path)) ||
132
+ (@secure && (url.scheme != 'https')) )
133
+ return false
134
+ else
135
+ return true
136
+ end
137
+ end
138
+
139
+ def join_quotedstr(array, sep)
140
+ ret = Array.new
141
+ old_elem = nil
142
+ array.each{|elem|
143
+ if (elem.scan(/"/).length % 2) == 0
144
+ if old_elem
145
+ old_elem << sep << elem
146
+ else
147
+ ret << elem
148
+ old_elem = nil
149
+ end
150
+ else
151
+ if old_elem
152
+ old_elem << sep << elem
153
+ ret << old_elem
154
+ old_elem = nil
155
+ else
156
+ old_elem = elem.dup
157
+ end
158
+ end
159
+ }
160
+ ret
161
+ end
162
+
163
+ def parse(str, url)
164
+ @url = url
165
+ # TODO: should not depend on join_quotedstr. scan with escape like CSV.
166
+ cookie_elem = str.split(/;/)
167
+ cookie_elem = join_quotedstr(cookie_elem, ';')
168
+ cookie_elem -= [""] # del empty elements, a cookie might included ";;"
169
+ first_elem = cookie_elem.shift
170
+ if first_elem !~ /([^=]*)(\=(.*))?/
171
+ return
172
+ ## raise ArgumentError 'invalid cookie value'
173
+ end
174
+ @name = $1.strip
175
+ @value = normalize_cookie_value($3)
176
+ cookie_elem.each{|pair|
177
+ key, value = pair.split(/=/, 2) ## value may nil
178
+ key.strip!
179
+ value = normalize_cookie_value(value)
180
+ case key.downcase
181
+ when 'domain'
182
+ @domain = value
183
+ when 'expires'
184
+ @expires = nil
185
+ begin
186
+ @expires = Time.parse(value).gmtime if value
187
+ rescue ArgumentError
188
+ end
189
+ when 'path'
190
+ @path = value
191
+ when 'secure'
192
+ @secure = true ## value may nil, but must 'true'.
193
+ when 'httponly'
194
+ @http_only = true ## value may nil, but must 'true'.
195
+ else
196
+ ## ignore
197
+ end
198
+ }
199
+ end
200
+
201
+ private
202
+
203
+ def normalize_cookie_value(value)
204
+ if value
205
+ value = value.strip.sub(/\A"(.*)"\z/) { $1 }
206
+ value = nil if value.empty?
207
+ end
208
+ value
209
+ end
210
+ end
211
+
212
+ class CookieManager
213
+ include CookieUtils
214
+
215
+ ### errors
216
+ class Error < StandardError; end
217
+ class ErrorOverrideOK < Error; end
218
+ class SpecialError < Error; end
219
+
220
+ attr_reader :cookies
221
+ attr_accessor :cookies_file
222
+ attr_accessor :accept_domains, :reject_domains
223
+
224
+ def initialize(file=nil)
225
+ @cookies = Array.new
226
+ @cookies.extend(MonitorMixin)
227
+ @cookies_file = file
228
+ @is_saved = true
229
+ @reject_domains = Array.new
230
+ @accept_domains = Array.new
231
+ @netscape_rule = false
232
+ end
233
+
234
+ def cookies=(cookies)
235
+ @cookies = cookies
236
+ @cookies.extend(MonitorMixin)
237
+ end
238
+
239
+ def save_all_cookies(force = nil, save_unused = true, save_discarded = true)
240
+ @cookies.synchronize do
241
+ check_expired_cookies
242
+ if @is_saved and !force
243
+ return
244
+ end
245
+ File.open(@cookies_file, 'w') do |f|
246
+ @cookies.each do |cookie|
247
+ if (cookie.use? or save_unused) and
248
+ (!cookie.discard? or save_discarded)
249
+ f.print(cookie.url.to_s,"\t",
250
+ cookie.name,"\t",
251
+ cookie.value,"\t",
252
+ cookie.expires.to_i,"\t",
253
+ cookie.domain,"\t",
254
+ cookie.path,"\t",
255
+ cookie.flag,"\n")
256
+ end
257
+ end
258
+ end
259
+ end
260
+ @is_saved = true
261
+ end
262
+
263
+ def save_cookies(force = nil)
264
+ save_all_cookies(force, false, false)
265
+ end
266
+
267
+ def check_expired_cookies
268
+ @cookies.reject!{|cookie|
269
+ is_expired = (cookie.expires && (cookie.expires < Time.now.gmtime))
270
+ if is_expired && !cookie.discard?
271
+ @is_saved = false
272
+ end
273
+ is_expired
274
+ }
275
+ end
276
+
277
+ def parse(str, url)
278
+ cookie = WebAgent::Cookie.new
279
+ cookie.parse(str, url)
280
+ add(cookie)
281
+ end
282
+
283
+ def find(url)
284
+ return nil if @cookies.empty?
285
+
286
+ cookie_list = Array.new
287
+ @cookies.each{|cookie|
288
+ is_expired = (cookie.expires && (cookie.expires < Time.now.gmtime))
289
+ if cookie.use? && !is_expired && cookie.match?(url)
290
+ if cookie_list.select{|c1| c1.name == cookie.name}.empty?
291
+ cookie_list << cookie
292
+ end
293
+ end
294
+ }
295
+ return make_cookie_str(cookie_list)
296
+ end
297
+
298
+ def add(given)
299
+ check_domain(given.domain, given.url.host, given.override?)
300
+
301
+ domain = given.domain || given.url.host
302
+ path = given.path || given.url.path.sub(%r|/[^/]*\z|, '')
303
+
304
+ cookie = nil
305
+ @cookies.synchronize do
306
+ cookie = @cookies.find { |c|
307
+ c.domain == domain && c.path == path && c.name == given.name
308
+ }
309
+ if !cookie
310
+ cookie = WebAgent::Cookie.new
311
+ cookie.use = true
312
+ @cookies << cookie
313
+ end
314
+ check_expired_cookies
315
+ end
316
+
317
+ cookie.domain = domain
318
+ cookie.path = path
319
+ cookie.url = given.url
320
+ cookie.name = given.name
321
+ cookie.value = given.value
322
+ cookie.expires = given.expires
323
+ cookie.secure = given.secure?
324
+ cookie.http_only = given.http_only?
325
+ cookie.domain_orig = given.domain
326
+ cookie.path_orig = given.path
327
+
328
+ if cookie.discard? || cookie.expires == nil
329
+ cookie.discard = true
330
+ else
331
+ cookie.discard = false
332
+ @is_saved = false
333
+ end
334
+ end
335
+
336
+ def load_cookies
337
+ return if !File.readable?(@cookies_file)
338
+ @cookies.synchronize do
339
+ @cookies.clear
340
+ File.open(@cookies_file,'r'){|f|
341
+ while line = f.gets
342
+ cookie = WebAgent::Cookie.new
343
+ @cookies << cookie
344
+ col = line.chomp.split(/\t/)
345
+ cookie.url = HTTPClient::Util.urify(col[0])
346
+ cookie.name = col[1]
347
+ cookie.value = col[2]
348
+ if col[3].empty? or col[3] == '0'
349
+ cookie.expires = nil
350
+ else
351
+ cookie.expires = Time.at(col[3].to_i).gmtime
352
+ end
353
+ cookie.domain = col[4]
354
+ cookie.path = col[5]
355
+ cookie.set_flag(col[6])
356
+ end
357
+ }
358
+ end
359
+ end
360
+
361
+ # Who use it?
362
+ def check_cookie_accept_domain(domain)
363
+ unless domain
364
+ return false
365
+ end
366
+ @accept_domains.each{|dom|
367
+ if domain_match(domain, dom)
368
+ return true
369
+ end
370
+ }
371
+ @reject_domains.each{|dom|
372
+ if domain_match(domain, dom)
373
+ return false
374
+ end
375
+ }
376
+ return true
377
+ end
378
+
379
+ private
380
+
381
+ def make_cookie_str(cookie_list)
382
+ if cookie_list.empty?
383
+ return nil
384
+ end
385
+
386
+ ret = ''
387
+ c = cookie_list.shift
388
+ ret += "#{c.name}=#{c.value}"
389
+ cookie_list.each{|cookie|
390
+ ret += "; #{cookie.name}=#{cookie.value}"
391
+ }
392
+ return ret
393
+ end
394
+
395
+ # for conformance to http://wp.netscape.com/newsref/std/cookie_spec.html
396
+ attr_accessor :netscape_rule
397
+ SPECIAL_DOMAIN = [".com",".edu",".gov",".mil",".net",".org",".int"]
398
+
399
+ def check_domain(domain, hostname, override)
400
+ return unless domain
401
+
402
+ # [DRAFT 12] s. 4.2.2 (does not apply in the case that
403
+ # host name is the same as domain attribute for version 0
404
+ # cookie)
405
+ # I think that this rule has almost the same effect as the
406
+ # tail match of [NETSCAPE].
407
+ if domain !~ /^\./ && hostname != domain
408
+ domain = '.'+domain
409
+ end
410
+ # [NETSCAPE] rule
411
+ if @netscape_rule
412
+ n = domain.scan(/\./).length
413
+ if n < 2
414
+ cookie_error(SpecialError.new, override)
415
+ elsif n == 2
416
+ ## [NETSCAPE] rule
417
+ ok = SPECIAL_DOMAIN.select{|sdomain|
418
+ sdomain == domain[-(sdomain.length)..-1]
419
+ }
420
+ if ok.empty?
421
+ cookie_error(SpecialError.new, override)
422
+ end
423
+ end
424
+ end
425
+ # this implementation does not check RFC2109 4.3.2 case 2;
426
+ # the portion of host not in domain does not contain a dot.
427
+ # according to nsCookieService.cpp in Firefox 3.0.4, Firefox 3.0.4
428
+ # and IE does not check, too.
429
+ end
430
+
431
+ # not tested well; used only netscape_rule = true.
432
+ def cookie_error(err, override)
433
+ if !err.kind_of?(ErrorOverrideOK) || !override
434
+ raise err
435
+ end
436
+ end
437
+ end
438
+ end