rack-cache 1.9.0 → 1.12.1
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.
- checksums.yaml +4 -4
- data/CHANGES +17 -0
- data/README.md +16 -4
- data/lib/rack/cache/context.rb +25 -7
- data/lib/rack/cache/entity_store.rb +4 -4
- data/lib/rack/cache/key.rb +21 -5
- data/lib/rack/cache/meta_store.rb +4 -3
- data/lib/rack/cache/options.rb +5 -0
- data/lib/rack/cache/response.rb +1 -0
- data/lib/rack/cache/storage.rb +7 -6
- metadata +4 -5
    
        checksums.yaml
    CHANGED
    
    | @@ -1,7 +1,7 @@ | |
| 1 1 | 
             
            ---
         | 
| 2 2 | 
             
            SHA256:
         | 
| 3 | 
            -
              metadata.gz:  | 
| 4 | 
            -
              data.tar.gz:  | 
| 3 | 
            +
              metadata.gz: faa3fda2990457be314ac3643ed59e28487459ed4022c6ef1682c4922389dee7
         | 
| 4 | 
            +
              data.tar.gz: baf2634fa406e4c6da7e17339b4309217ba5ad99cda998fc67a0eeff369b513c
         | 
| 5 5 | 
             
            SHA512:
         | 
| 6 | 
            -
              metadata.gz:  | 
| 7 | 
            -
              data.tar.gz:  | 
| 6 | 
            +
              metadata.gz: 91d096f1cd9808a4d7983175af2549bc900a2b6ce3547799b30c11c8f9b233d874f0f1c6e64a36dbefda3161d12df50c696ba32e05f85ec7c34a825183499c01
         | 
| 7 | 
            +
              data.tar.gz: 510a3c91dc5b06a6f87985f846a001ab543679e909902cdef7a2ebf96bd3efdedfc9e2b778d959e51b379dddf5fbb8d3ae4adac085a18228af2694c285327df7
         | 
    
        data/CHANGES
    CHANGED
    
    | @@ -1,3 +1,20 @@ | |
| 1 | 
            +
            ## 1.12.0
         | 
| 2 | 
            +
             | 
| 3 | 
            +
             * Add a fault_tolerant flag to fail-over to stale cache
         | 
| 4 | 
            +
             | 
| 5 | 
            +
            ## 1.11.1
         | 
| 6 | 
            +
             | 
| 7 | 
            +
             * when ignoring parts of the query, remove query in key when all params are ignored
         | 
| 8 | 
            +
             | 
| 9 | 
            +
            ## 1.11.0
         | 
| 10 | 
            +
             | 
| 11 | 
            +
             * Add a proc to allow ignoring parts of the query string in the key
         | 
| 12 | 
            +
             | 
| 13 | 
            +
            ## 1.10.0
         | 
| 14 | 
            +
             | 
| 15 | 
            +
              * Pass Options To Underlying Storage Driver
         | 
| 16 | 
            +
              * bump required ruby version to 2.3
         | 
| 17 | 
            +
             | 
| 1 18 | 
             
            ## 1.9.0
         | 
| 2 19 |  | 
| 3 20 | 
             
              * make purge not raise when not implemented
         | 
    
        data/README.md
    CHANGED
    
    | @@ -16,7 +16,7 @@ validation (Last-Modified, ETag) information: | |
| 16 16 |  | 
| 17 17 | 
             
            For more information about Rack::Cache features and usage, see:
         | 
| 18 18 |  | 
| 19 | 
            -
             | 
| 19 | 
            +
            https://rtomayko.github.com/rack-cache/
         | 
| 20 20 |  | 
| 21 21 | 
             
            Rack::Cache is not overly optimized for performance. The main goal of the
         | 
| 22 22 | 
             
            project is to provide a portable, easy-to-configure, and standards-based
         | 
| @@ -70,7 +70,7 @@ You should now see `Rack::Cache` listed in the middleware pipeline: | |
| 70 70 |  | 
| 71 71 | 
             
                rake middleware
         | 
| 72 72 |  | 
| 73 | 
            -
            [more information]( | 
| 73 | 
            +
            [more information](https://snippets.aktagon.com/snippets/302-how-to-setup-and-use-rack-cache-with-rails)
         | 
| 74 74 |  | 
| 75 75 | 
             
            Using with Dalli
         | 
| 76 76 | 
             
            ----------------
         | 
| @@ -97,7 +97,7 @@ Does not persist response bodies (no disk/memory used).<br/> | |
| 97 97 | 
             
            Responses from the cache will have an empty body.<br/>
         | 
| 98 98 | 
             
            Clients must ignore these empty cached response (check for X-Rack-Cache response header).<br/>
         | 
| 99 99 | 
             
            Atm cannot handle streamed responses, patch needed.
         | 
| 100 | 
            -
             | 
| 100 | 
            +
             | 
| 101 101 | 
             
            ```Ruby
         | 
| 102 102 | 
             
            require 'rack/cache'
         | 
| 103 103 |  | 
| @@ -109,6 +109,18 @@ use Rack::Cache, | |
| 109 109 | 
             
            run app
         | 
| 110 110 | 
             
            ```
         | 
| 111 111 |  | 
| 112 | 
            +
            Ignoring tracking parameters in cache keys
         | 
| 113 | 
            +
            -----------------
         | 
| 114 | 
            +
             | 
| 115 | 
            +
            It's fairly common to include tracking parameters which don't affect the content
         | 
| 116 | 
            +
            of the page. Since Rack::Cache uses the full URL as part of the cache key, this
         | 
| 117 | 
            +
            can cause unneeded churn in your cache. If you're using the default key class
         | 
| 118 | 
            +
            `Rack::Cache::Key`, you can configure a proc to ignore certain keys/values like
         | 
| 119 | 
            +
            so:
         | 
| 120 | 
            +
             | 
| 121 | 
            +
            ```Ruby
         | 
| 122 | 
            +
            Rack::Cache::Key.query_string_ignore = proc { |k, v| k =~ /^(trk|utm)_/ }
         | 
| 123 | 
            +
            ```
         | 
| 124 | 
            +
             | 
| 112 125 | 
             
            License: MIT<br/>
         | 
| 113 126 | 
             
            [](https://travis-ci.org/rtomayko/rack-cache)
         | 
| 114 | 
            -
             | 
    
        data/lib/rack/cache/context.rb
    CHANGED
    
    | @@ -19,6 +19,7 @@ module Rack::Cache | |
| 19 19 | 
             
                  @backend = backend
         | 
| 20 20 | 
             
                  @trace = []
         | 
| 21 21 | 
             
                  @env = nil
         | 
| 22 | 
            +
                  @options = options
         | 
| 22 23 |  | 
| 23 24 | 
             
                  initialize_options options
         | 
| 24 25 | 
             
                  yield self if block_given?
         | 
| @@ -31,14 +32,14 @@ module Rack::Cache | |
| 31 32 | 
             
                # value effects the result of this method immediately.
         | 
| 32 33 | 
             
                def metastore
         | 
| 33 34 | 
             
                  uri = options['rack-cache.metastore']
         | 
| 34 | 
            -
                  storage.resolve_metastore_uri(uri)
         | 
| 35 | 
            +
                  storage.resolve_metastore_uri(uri, @options)
         | 
| 35 36 | 
             
                end
         | 
| 36 37 |  | 
| 37 38 | 
             
                # The configured EntityStore instance. Changing the rack-cache.entitystore
         | 
| 38 39 | 
             
                # value effects the result of this method immediately.
         | 
| 39 40 | 
             
                def entitystore
         | 
| 40 41 | 
             
                  uri = options['rack-cache.entitystore']
         | 
| 41 | 
            -
                  storage.resolve_entitystore_uri(uri)
         | 
| 42 | 
            +
                  storage.resolve_entitystore_uri(uri, @options)
         | 
| 42 43 | 
             
                end
         | 
| 43 44 |  | 
| 44 45 | 
             
                # The Rack call interface. The receiver acts as a prototype and runs
         | 
| @@ -160,10 +161,12 @@ module Rack::Cache | |
| 160 161 | 
             
                end
         | 
| 161 162 |  | 
| 162 163 | 
             
                # Try to serve the response from cache. When a matching cache entry is
         | 
| 163 | 
            -
                # found and is fresh, use it as the response without forwarding any
         | 
| 164 | 
            -
                #  | 
| 165 | 
            -
                #  | 
| 166 | 
            -
                #  | 
| 164 | 
            +
                # found and is fresh, use it as the response without forwarding any request
         | 
| 165 | 
            +
                # to the backend. When a matching cache entry is found but is stale, attempt
         | 
| 166 | 
            +
                # to #validate the entry with the backend using conditional GET.
         | 
| 167 | 
            +
                # If validation raises an exception and fault tolerant caching is enabled,
         | 
| 168 | 
            +
                # serve the stale cache entry.
         | 
| 169 | 
            +
                # When no matching cache entry is found, trigger miss processing.
         | 
| 167 170 | 
             
                def lookup
         | 
| 168 171 | 
             
                  if @request.no_cache? && allow_reload?
         | 
| 169 172 | 
             
                    record :reload
         | 
| @@ -182,7 +185,11 @@ module Rack::Cache | |
| 182 185 | 
             
                        entry
         | 
| 183 186 | 
             
                      else
         | 
| 184 187 | 
             
                        record :stale
         | 
| 185 | 
            -
                         | 
| 188 | 
            +
                        if fault_tolerant?
         | 
| 189 | 
            +
                          validate_with_stale_cache_failover(entry)
         | 
| 190 | 
            +
                        else
         | 
| 191 | 
            +
                          validate(entry)
         | 
| 192 | 
            +
                        end
         | 
| 186 193 | 
             
                      end
         | 
| 187 194 | 
             
                    else
         | 
| 188 195 | 
             
                      record :miss
         | 
| @@ -191,6 +198,17 @@ module Rack::Cache | |
| 191 198 | 
             
                  end
         | 
| 192 199 | 
             
                end
         | 
| 193 200 |  | 
| 201 | 
            +
                # Returns stale cache on exception.
         | 
| 202 | 
            +
                def validate_with_stale_cache_failover(entry)
         | 
| 203 | 
            +
                  validate(entry)
         | 
| 204 | 
            +
                rescue => e
         | 
| 205 | 
            +
                  record :connnection_failed
         | 
| 206 | 
            +
                  age = entry.age.to_s
         | 
| 207 | 
            +
                  entry.headers['Age'] = age
         | 
| 208 | 
            +
                  record "Fail-over to stale cache data with age #{age} due to #{e.class.name}: #{e}"
         | 
| 209 | 
            +
                  entry
         | 
| 210 | 
            +
                end
         | 
| 211 | 
            +
             | 
| 194 212 | 
             
                # Validate that the cache entry is fresh. The original request is used
         | 
| 195 213 | 
             
                # as a template for a conditional GET request with the backend.
         | 
| 196 214 | 
             
                def validate(entry)
         | 
| @@ -33,10 +33,10 @@ module Rack::Cache | |
| 33 33 |  | 
| 34 34 | 
             
                # Stores entity bodies on the heap using a Hash object.
         | 
| 35 35 | 
             
                class Heap < EntityStore
         | 
| 36 | 
            -
             | 
| 37 36 | 
             
                  # Create the store with the specified backing Hash.
         | 
| 38 | 
            -
                  def initialize(hash={})
         | 
| 37 | 
            +
                  def initialize(hash={}, options = {})
         | 
| 39 38 | 
             
                    @hash = hash
         | 
| 39 | 
            +
                    @options = options
         | 
| 40 40 | 
             
                  end
         | 
| 41 41 |  | 
| 42 42 | 
             
                  # Determine whether the response body with the specified key (SHA1)
         | 
| @@ -71,8 +71,8 @@ module Rack::Cache | |
| 71 71 | 
             
                    nil
         | 
| 72 72 | 
             
                  end
         | 
| 73 73 |  | 
| 74 | 
            -
                  def self.resolve(uri)
         | 
| 75 | 
            -
                    new
         | 
| 74 | 
            +
                  def self.resolve(uri, options = {})
         | 
| 75 | 
            +
                    new({}, options)
         | 
| 76 76 | 
             
                  end
         | 
| 77 77 | 
             
                end
         | 
| 78 78 |  | 
    
        data/lib/rack/cache/key.rb
    CHANGED
    
    | @@ -4,6 +4,21 @@ module Rack::Cache | |
| 4 4 | 
             
              class Key
         | 
| 5 5 | 
             
                include Rack::Utils
         | 
| 6 6 |  | 
| 7 | 
            +
                # A proc for ignoring parts of query strings when generating a key. This is
         | 
| 8 | 
            +
                # useful when you have parameters like `utm` or `trk` that don't affect the
         | 
| 9 | 
            +
                # content on the page and are unique per-visitor or campaign. Parameters
         | 
| 10 | 
            +
                # like these will be part of the key and cause a lot of churn.
         | 
| 11 | 
            +
                #
         | 
| 12 | 
            +
                # The block will be passed a key and value which are the name and value of
         | 
| 13 | 
            +
                # that parameter.
         | 
| 14 | 
            +
                #
         | 
| 15 | 
            +
                # Example:
         | 
| 16 | 
            +
                #   `Rack::Cache::Key.query_string_ignore = proc { |k, v| k =~ /^(trk|utm)_/ }`
         | 
| 17 | 
            +
                #
         | 
| 18 | 
            +
                class << self
         | 
| 19 | 
            +
                  attr_accessor :query_string_ignore
         | 
| 20 | 
            +
                end
         | 
| 21 | 
            +
             | 
| 7 22 | 
             
                # Implement .call, since it seems like the "Rack-y" thing to do. Plus, it
         | 
| 8 23 | 
             
                # opens the door for cache key generators to just be blocks.
         | 
| 9 24 | 
             
                def self.call(request)
         | 
| @@ -42,11 +57,12 @@ module Rack::Cache | |
| 42 57 | 
             
                def query_string
         | 
| 43 58 | 
             
                  return nil if @request.query_string.to_s.empty?
         | 
| 44 59 |  | 
| 45 | 
            -
                  @request.query_string.split(/[&;] */n) | 
| 46 | 
            -
             | 
| 47 | 
            -
             | 
| 48 | 
            -
             | 
| 49 | 
            -
             | 
| 60 | 
            +
                  parts = @request.query_string.split(/[&;] */n)
         | 
| 61 | 
            +
                  parts.map! { |p| p.split('=', 2).map!{ |s| unescape(s) } }
         | 
| 62 | 
            +
                  parts.sort!
         | 
| 63 | 
            +
                  parts.reject!(&self.class.query_string_ignore)
         | 
| 64 | 
            +
                  parts.map! { |k,v| "#{escape(k)}=#{escape(v)}" }
         | 
| 65 | 
            +
                  parts.empty? ? nil : parts.join('&')
         | 
| 50 66 | 
             
                end
         | 
| 51 67 | 
             
              end
         | 
| 52 68 | 
             
            end
         | 
| @@ -198,8 +198,9 @@ module Rack::Cache | |
| 198 198 | 
             
                # Concrete MetaStore implementation that uses a simple Hash to store
         | 
| 199 199 | 
             
                # request/response pairs on the heap.
         | 
| 200 200 | 
             
                class Heap < MetaStore
         | 
| 201 | 
            -
                  def initialize(hash={})
         | 
| 201 | 
            +
                  def initialize(hash={}, options = {})
         | 
| 202 202 | 
             
                    @hash = hash
         | 
| 203 | 
            +
                    @options = options
         | 
| 203 204 | 
             
                  end
         | 
| 204 205 |  | 
| 205 206 | 
             
                  def read(key)
         | 
| @@ -223,8 +224,8 @@ module Rack::Cache | |
| 223 224 | 
             
                    @hash
         | 
| 224 225 | 
             
                  end
         | 
| 225 226 |  | 
| 226 | 
            -
                  def self.resolve(uri)
         | 
| 227 | 
            -
                    new
         | 
| 227 | 
            +
                  def self.resolve(uri, options = {})
         | 
| 228 | 
            +
                    new({}, options)
         | 
| 228 229 | 
             
                  end
         | 
| 229 230 | 
             
                end
         | 
| 230 231 |  | 
    
        data/lib/rack/cache/options.rb
    CHANGED
    
    | @@ -107,6 +107,10 @@ module Rack::Cache | |
| 107 107 | 
             
                # be used.
         | 
| 108 108 | 
             
                option_accessor :use_native_ttl
         | 
| 109 109 |  | 
| 110 | 
            +
                # Specifies whether to serve a request from a stale cache entry if
         | 
| 111 | 
            +
                # the attempt to revalidate the cache entry raises an exception.
         | 
| 112 | 
            +
                option_accessor :fault_tolerant
         | 
| 113 | 
            +
             | 
| 110 114 | 
             
                # The underlying options Hash. During initialization (or outside of a
         | 
| 111 115 | 
             
                # request), this is a default values Hash. During a request, this is the
         | 
| 112 116 | 
             
                # Rack environment Hash. The default values Hash is merged in underneath
         | 
| @@ -149,6 +153,7 @@ module Rack::Cache | |
| 149 153 | 
             
                    'rack-cache.allow_reload'     => false,
         | 
| 150 154 | 
             
                    'rack-cache.allow_revalidate' => false,
         | 
| 151 155 | 
             
                    'rack-cache.use_native_ttl'   => false,
         | 
| 156 | 
            +
                    'rack-cache.fault_tolerant'   => false,
         | 
| 152 157 | 
             
                  }
         | 
| 153 158 | 
             
                  self.options = options
         | 
| 154 159 | 
             
                end
         | 
    
        data/lib/rack/cache/response.rb
    CHANGED
    
    
    
        data/lib/rack/cache/storage.rb
    CHANGED
    
    | @@ -14,12 +14,12 @@ module Rack::Cache | |
| 14 14 | 
             
                  @entitystores = {}
         | 
| 15 15 | 
             
                end
         | 
| 16 16 |  | 
| 17 | 
            -
                def resolve_metastore_uri(uri)
         | 
| 18 | 
            -
                  @metastores[uri.to_s] ||= create_store(MetaStore, uri)
         | 
| 17 | 
            +
                def resolve_metastore_uri(uri, options = {})
         | 
| 18 | 
            +
                  @metastores[uri.to_s] ||= create_store(MetaStore, uri, options)
         | 
| 19 19 | 
             
                end
         | 
| 20 20 |  | 
| 21 | 
            -
                def resolve_entitystore_uri(uri)
         | 
| 22 | 
            -
                  @entitystores[uri.to_s] ||= create_store(EntityStore, uri)
         | 
| 21 | 
            +
                def resolve_entitystore_uri(uri, options = {})
         | 
| 22 | 
            +
                  @entitystores[uri.to_s] ||= create_store(EntityStore, uri, options)
         | 
| 23 23 | 
             
                end
         | 
| 24 24 |  | 
| 25 25 | 
             
                def clear
         | 
| @@ -30,12 +30,13 @@ module Rack::Cache | |
| 30 30 |  | 
| 31 31 | 
             
              private
         | 
| 32 32 |  | 
| 33 | 
            -
                def create_store(type, uri)
         | 
| 33 | 
            +
                def create_store(type, uri, options = {})
         | 
| 34 34 | 
             
                  if uri.respond_to?(:scheme) || uri.respond_to?(:to_str)
         | 
| 35 35 | 
             
                    uri = URI.parse(uri) unless uri.respond_to?(:scheme)
         | 
| 36 36 | 
             
                    if type.const_defined?(uri.scheme.upcase)
         | 
| 37 37 | 
             
                      klass = type.const_get(uri.scheme.upcase)
         | 
| 38 | 
            -
                      klass.resolve(uri)
         | 
| 38 | 
            +
                      return klass.resolve(uri) if klass.method(:resolve).arity == 1
         | 
| 39 | 
            +
                      klass.resolve(uri, options)
         | 
| 39 40 | 
             
                    else
         | 
| 40 41 | 
             
                      fail "Unknown storage provider: #{uri.to_s}"
         | 
| 41 42 | 
             
                    end
         | 
    
        metadata
    CHANGED
    
    | @@ -1,14 +1,14 @@ | |
| 1 1 | 
             
            --- !ruby/object:Gem::Specification
         | 
| 2 2 | 
             
            name: rack-cache
         | 
| 3 3 | 
             
            version: !ruby/object:Gem::Version
         | 
| 4 | 
            -
              version: 1. | 
| 4 | 
            +
              version: 1.12.1
         | 
| 5 5 | 
             
            platform: ruby
         | 
| 6 6 | 
             
            authors:
         | 
| 7 7 | 
             
            - Ryan Tomayko
         | 
| 8 8 | 
             
            autorequire: 
         | 
| 9 9 | 
             
            bindir: bin
         | 
| 10 10 | 
             
            cert_chain: []
         | 
| 11 | 
            -
            date:  | 
| 11 | 
            +
            date: 2020-10-16 00:00:00.000000000 Z
         | 
| 12 12 | 
             
            dependencies:
         | 
| 13 13 | 
             
            - !ruby/object:Gem::Dependency
         | 
| 14 14 | 
             
              name: rack
         | 
| @@ -156,15 +156,14 @@ required_ruby_version: !ruby/object:Gem::Requirement | |
| 156 156 | 
             
              requirements:
         | 
| 157 157 | 
             
              - - ">="
         | 
| 158 158 | 
             
                - !ruby/object:Gem::Version
         | 
| 159 | 
            -
                  version: 2. | 
| 159 | 
            +
                  version: 2.3.0
         | 
| 160 160 | 
             
            required_rubygems_version: !ruby/object:Gem::Requirement
         | 
| 161 161 | 
             
              requirements:
         | 
| 162 162 | 
             
              - - ">="
         | 
| 163 163 | 
             
                - !ruby/object:Gem::Version
         | 
| 164 164 | 
             
                  version: '0'
         | 
| 165 165 | 
             
            requirements: []
         | 
| 166 | 
            -
             | 
| 167 | 
            -
            rubygems_version: 2.7.6
         | 
| 166 | 
            +
            rubygems_version: 3.1.3
         | 
| 168 167 | 
             
            signing_key: 
         | 
| 169 168 | 
             
            specification_version: 4
         | 
| 170 169 | 
             
            summary: HTTP Caching for Rack
         |