Permalink
Browse files

Rescue from exceptions raised by the metastore and pass on the request

  • Loading branch information...
josh committed Sep 25, 2009
1 parent e51b1fb commit 7bcd0cec2723b91ee0d557153134d457219895ba
Showing with 57 additions and 12 deletions.
  1. +32 −12 lib/rack/cache/context.rb
  2. +25 −0 test/context_test.rb
View
@@ -133,8 +133,12 @@ def pass
# Invalidate POST, PUT, DELETE and all methods not understood by this cache
# See RFC2616 13.10
def invalidate
- record :invalidate
metastore.invalidate(@request, entitystore)
+ rescue Exception => e
+ log_error(e)
+ pass
+ else
+ record :invalidate
pass
end
@@ -147,18 +151,26 @@ def lookup
if @request.no_cache? && allow_reload?
record :reload
fetch
- elsif entry = metastore.lookup(@request, entitystore)
- if fresh_enough?(entry)
- record :fresh
- entry.headers['Age'] = entry.age.to_s
- entry
+ else
+ begin
+ entry = metastore.lookup(@request, entitystore)
+ rescue Exception => e
+ log_error(e)
+ return pass
+ end
+ if entry
+ if fresh_enough?(entry)
+ record :fresh
+ entry.headers['Age'] = entry.age.to_s
+ entry
+ else
+ record :stale
+ validate(entry)
+ end
else
- record :stale
- validate(entry)
+ record :miss
+ fetch
end
- else
- record :miss
- fetch
end
end
@@ -225,9 +237,17 @@ def fetch
# Write the response to the cache.
def store(response)
- record :store
metastore.store(@request, response, entitystore)
response.headers['Age'] = response.age.to_s
+ rescue Exception => e
+ log_error(e)
+ nil
+ else
+ record :store
+ end
+
+ def log_error(exception)
+ @env['rack.errors'].write("cache error: #{exception.message}\n#{exception.backtrace.join("\n")}\n")
end
end
end
View
@@ -746,4 +746,29 @@
response['X-Response-Count'].should.equal '3'
end
end
+
+ it 'passes if there was a metastore exception' do
+ respond_with 200, 'Cache-Control' => 'max-age=10000' do |req,res|
+ res.body = ['Hello World']
+ end
+
+ get '/'
+ response.should.be.ok
+ response.body.should.equal 'Hello World'
+ cache.trace.should.include :store
+
+ get '/' do |cache|
+ cache.meta_def(:metastore) { raise Timeout::Error }
+ end
+ response.should.be.ok
+ response.body.should.equal 'Hello World'
+ cache.trace.should.include :pass
+
+ post '/' do |cache|
+ cache.meta_def(:metastore) { raise Timeout::Error }
+ end
+ response.should.be.ok
+ response.body.should.equal 'Hello World'
+ cache.trace.should.include :pass
+ end
end

0 comments on commit 7bcd0ce

Please sign in to comment.