Skip to content

Commit

Permalink
Eagerly load Signed and Permanent cookies
Browse files Browse the repository at this point in the history
  • Loading branch information
spastorino committed Apr 7, 2011
1 parent 29592a7 commit dffeda3
Showing 1 changed file with 17 additions and 10 deletions.
27 changes: 17 additions & 10 deletions actionpack/lib/action_dispatch/middleware/cookies.rb
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,8 @@ def initialize(secret = nil, host = nil, secure = false)
@host = host
@secure = secure
@cookies = {}
@permanent = PermanentCookieJar.new(self, @secret)
@signed = @secret && SignedCookieJar.new(self, @secret)
end

alias :closed? :frozen?
Expand Down Expand Up @@ -193,9 +195,7 @@ def delete(key, options = {})
#
# cookies.permanent.signed[:remember_me] = current_user.id
# # => Set-Cookie: remember_me=BAhU--848956038e692d7046deab32b7131856ab20e14e; path=/; expires=Sun, 16-Dec-2029 03:24:16 GMT
def permanent
@permanent ||= PermanentCookieJar.new(self, @secret)
end
attr_reader :permanent

# Returns a jar that'll automatically generate a signed representation of cookie value and verify it when reading from
# the cookie again. This is useful for creating cookies with values that the user is not supposed to change. If a signed
Expand All @@ -211,7 +211,8 @@ def permanent
#
# cookies.signed[:discount] # => 45
def signed
@signed ||= SignedCookieJar.new(self, @secret)
SignedCookieJar.ensure_secret_provided(@secret)
@signed
end

def write(headers)
Expand All @@ -228,7 +229,9 @@ def write_cookie?(cookie)

class PermanentCookieJar < CookieJar #:nodoc:
def initialize(parent_jar, secret)
@parent_jar, @secret = parent_jar, secret
@parent_jar = parent_jar
@secret = secret
@signed = @secret && SignedCookieJar.new(self, @secret)
end

def []=(key, options)
Expand All @@ -244,7 +247,8 @@ def []=(key, options)
end

def signed
@signed ||= SignedCookieJar.new(self, @secret)
SignedCookieJar.ensure_secret_provided(@secret)
@signed
end

def method_missing(method, *arguments, &block)
Expand All @@ -257,7 +261,8 @@ class SignedCookieJar < CookieJar #:nodoc:
SECRET_MIN_LENGTH = 30 # Characters

def initialize(parent_jar, secret)
ensure_secret_secure(secret)
self.class.ensure_secret_provided(secret)
self.class.ensure_secret_length(secret)
@parent_jar = parent_jar
@verifier = ActiveSupport::MessageVerifier.new(secret)
end
Expand Down Expand Up @@ -289,17 +294,19 @@ def method_missing(method, *arguments, &block)

protected

# To prevent users from using something insecure like "Password" we make sure that the
# secret they've provided is at least 30 characters in length.
def ensure_secret_secure(secret)
def self.ensure_secret_provided(secret)
if secret.blank?
raise ArgumentError, "A secret is required to generate an " +
"integrity hash for cookie session data. Use " +
"config.secret_token = \"some secret phrase of at " +
"least #{SECRET_MIN_LENGTH} characters\"" +
"in config/initializers/secret_token.rb"
end
end

# To prevent users from using something insecure like "Password" we make sure that the
# secret they've provided is at least 30 characters in length.
def self.ensure_secret_length(secret)
if secret.length < SECRET_MIN_LENGTH
raise ArgumentError, "Secret should be something secure, " +
"like \"#{ActiveSupport::SecureRandom.hex(16)}\". The value you " +
Expand Down

0 comments on commit dffeda3

Please sign in to comment.