class Rack::Session::Cookie

def delete_session(req, session_id, options)

def delete_session(req, session_id, options)
  # Nothing to do here, data is in the client
  generate_sid unless options[:drop]
end

def digest_match?(data, digest)

def digest_match?(data, digest)
  return unless data && digest
  @secrets.any? do |secret|
    Rack::Utils.secure_compare(digest, generate_hmac(data, secret))
  end
end

def extract_session_id(request)

def extract_session_id(request)
  unpacked_cookie_data(request)["session_id"]
end

def find_session(req, sid)

def find_session(req, sid)
  data = unpacked_cookie_data(req)
  data = persistent_session_id!(data)
  [data["session_id"], data]
end

def generate_hmac(data, secret)

def generate_hmac(data, secret)
  OpenSSL::HMAC.hexdigest(@hmac.new, secret, data)
end

def initialize(app, options = {})

def initialize(app, options = {})
  @secrets = options.values_at(:secret, :old_secret).compact
  @hmac = options.fetch(:hmac, OpenSSL::Digest::SHA1)
  warn <<-MSG unless secure?(options)
  SECURITY WARNING: No secret option provided to Rack::Session::Cookie.
  This poses a security threat. It is strongly recommended that you
  provide a secret to prevent exploits that may be possible from crafted
  cookies. This will not be supported in future versions of Rack, and
  future versions will even invalidate your existing user cookies.
  Called from: #{caller[0]}.
  MSG
  @coder = options[:coder] ||= Base64::Marshal.new
  super(app, options.merge!(cookie_only: true))
end

def persistent_session_id!(data, sid = nil)

def persistent_session_id!(data, sid = nil)
  data ||= {}
  data["session_id"] ||= sid || generate_sid
  data
end

def secure?(options)

def secure?(options)
  @secrets.size >= 1 ||
  (options[:coder] && options[:let_coder_handle_secure_encoding])
end

def unpacked_cookie_data(request)

def unpacked_cookie_data(request)
  request.fetch_header(RACK_SESSION_UNPACKED_COOKIE_DATA) do |k|
    session_data = request.cookies[@key]
    if @secrets.size > 0 && session_data
      session_data, _, digest = session_data.rpartition('--')
      session_data = nil unless digest_match?(session_data, digest)
    end
    request.set_header(k, coder.decode(session_data) || {})
  end
end

def write_session(req, session_id, session, options)

def write_session(req, session_id, session, options)
  session = session.merge("session_id" => session_id)
  session_data = coder.encode(session)
  if @secrets.first
    session_data << "--#{generate_hmac(session_data, @secrets.first)}"
  end
  if session_data.size > (4096 - @key.size)
    req.get_header(RACK_ERRORS).puts("Warning! Rack::Session::Cookie data size exceeds 4K.")
    nil
  else
    SessionId.new(session_id, session_data)
  end
end