summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSantiago Pastorino <santiago@wyeworks.com>2015-05-20 07:41:48 -0300
committerSantiago Pastorino <santiago@wyeworks.com>2015-05-20 07:41:48 -0300
commitb102793a419135d792b29def4b0c368272723904 (patch)
tree88e23871a8cf0a6ee7009f0025ba062507ecc3ff
parent9099a0ee6a32d4f0a0058bbb1891c0b2853fcdcd (diff)
parente8dba2a73bb6681d863779365e9e3c14118cfa20 (diff)
downloadrack-b102793a419135d792b29def4b0c368272723904.tar.gz
Merge pull request #857 from jodosha/utils-parse-cookies
Extracted Rack::Utils.parse_cookies
-rw-r--r--lib/rack.rb1
-rw-r--r--lib/rack/request.rb12
-rw-r--r--lib/rack/utils.rb13
-rw-r--r--test/spec_utils.rb17
4 files changed, 33 insertions, 10 deletions
diff --git a/lib/rack.rb b/lib/rack.rb
index 56717be9..0dcb6ed3 100644
--- a/lib/rack.rb
+++ b/lib/rack.rb
@@ -38,6 +38,7 @@ module Rack
CACHE_CONTROL = 'Cache-Control'.freeze
CONTENT_LENGTH = 'Content-Length'.freeze
CONTENT_TYPE = 'Content-Type'.freeze
+ HTTP_COOKIE = 'HTTP_COOKIE'.freeze
GET = 'GET'.freeze
POST = 'POST'.freeze
diff --git a/lib/rack/request.rb b/lib/rack/request.rb
index e2cdaf47..7167f338 100644
--- a/lib/rack/request.rb
+++ b/lib/rack/request.rb
@@ -300,18 +300,10 @@ module Rack
def cookies
hash = @env["rack.request.cookie_hash"] ||= {}
- string = @env["HTTP_COOKIE"]
+ string = @env[HTTP_COOKIE]
return hash if string == @env["rack.request.cookie_string"]
- hash.clear
-
- # According to RFC 2109:
- # If multiple cookies satisfy the criteria above, they are ordered in
- # the Cookie header such that those with more specific Path attributes
- # precede those with less specific. Ordering with respect to other
- # attributes (e.g., Domain) is unspecified.
- cookies = Utils.parse_query(string, ';,') { |s| Rack::Utils.unescape(s) rescue s }
- cookies.each { |k,v| hash[k] = Array === v ? v.first : v }
+ hash.replace Utils.parse_cookies(@env)
@env["rack.request.cookie_string"] = string
hash
end
diff --git a/lib/rack/utils.rb b/lib/rack/utils.rb
index 759fa4d3..590b41bd 100644
--- a/lib/rack/utils.rb
+++ b/lib/rack/utils.rb
@@ -273,6 +273,19 @@ module Rack
end
module_function :select_best_encoding
+ def parse_cookies(env)
+ # According to RFC 2109:
+ # If multiple cookies satisfy the criteria above, they are ordered in
+ # the Cookie header such that those with more specific Path attributes
+ # precede those with less specific. Ordering with respect to other
+ # attributes (e.g., Domain) is unspecified.
+ Hash[].tap do |hash|
+ cookies = parse_query(env[HTTP_COOKIE], ';,') { |s| unescape(s) rescue s }
+ cookies.each { |k,v| hash[k] = Array === v ? v.first : v }
+ end
+ end
+ module_function :parse_cookies
+
def set_cookie_header!(header, key, value)
case value
when Hash
diff --git a/test/spec_utils.rb b/test/spec_utils.rb
index dbf958c4..0a295902 100644
--- a/test/spec_utils.rb
+++ b/test/spec_utils.rb
@@ -313,6 +313,23 @@ describe Rack::Utils do
Rack::Utils.build_query(key => nil).should.equal Rack::Utils.escape(key)
end
+ should "parse cookies" do
+ env = Rack::MockRequest.env_for("", "HTTP_COOKIE" => "zoo=m")
+ Rack::Utils.parse_cookies(env).should.equal({"zoo" => "m"})
+
+ env = Rack::MockRequest.env_for("", "HTTP_COOKIE" => "foo=%")
+ Rack::Utils.parse_cookies(env).should.equal({"foo" => "%"})
+
+ env = Rack::MockRequest.env_for("", "HTTP_COOKIE" => "foo=bar;foo=car")
+ Rack::Utils.parse_cookies(env).should.equal({"foo" => "bar"})
+
+ env = Rack::MockRequest.env_for("", "HTTP_COOKIE" => "foo=bar;quux=h&m")
+ Rack::Utils.parse_cookies(env).should.equal({"foo" => "bar", "quux" => "h&m"})
+
+ env = Rack::MockRequest.env_for("", "HTTP_COOKIE" => "foo=bar").freeze
+ Rack::Utils.parse_cookies(env).should.equal({"foo" => "bar"})
+ end
+
should "parse q-values" do
# XXX handle accept-extension
Rack::Utils.q_values("foo;q=0.5,bar,baz;q=0.9").should.equal [