From f9a792396ca6172e983b7eb4d7fa2b30b3e3ccef Mon Sep 17 00:00:00 2001 From: Joshua Peek Date: Wed, 23 Dec 2009 20:32:23 -0600 Subject: [PATCH] Set X-Cascade header when using pass Setting X-Cascade: pass allows middleware outside the Sinatra stack to continue trying to match the request. Signed-off-by: Ryan Tomayko --- lib/sinatra/base.rb | 7 ++++--- test/helpers_test.rb | 13 +++++++++++++ test/routing_test.rb | 26 ++++++++++++++++++++++++++ 3 files changed, 43 insertions(+), 3 deletions(-) diff --git a/lib/sinatra/base.rb b/lib/sinatra/base.rb index 47cf3bd6..405401d5 100644 --- a/lib/sinatra/base.rb +++ b/lib/sinatra/base.rb @@ -583,9 +583,10 @@ module Sinatra end def handle_not_found!(boom) - @env['sinatra.error'] = boom - @response.status = 404 - @response.body = ['

Not Found

'] + @env['sinatra.error'] = boom + @response.status = 404 + @response.headers['X-Cascade'] = 'pass' + @response.body = ['

Not Found

'] error_block! boom.class, NotFound end diff --git a/test/helpers_test.rb b/test/helpers_test.rb index 61ccdf8f..7c8c0920 100644 --- a/test/helpers_test.rb +++ b/test/helpers_test.rb @@ -142,6 +142,19 @@ class HelpersTest < Test::Unit::TestCase assert_equal 404, status assert_equal '', body end + + it 'does not set a X-Cascade header' do + mock_app { + get '/' do + not_found + fail 'not_found should halt' + end + } + + get '/' + assert_equal 404, status + assert_equal nil, response.headers['X-Cascade'] + end end describe 'headers' do diff --git a/test/routing_test.rb b/test/routing_test.rb index 6ef32547..9976b679 100644 --- a/test/routing_test.rb +++ b/test/routing_test.rb @@ -60,6 +60,15 @@ class RoutingTest < Test::Unit::TestCase assert_equal 404, status end + it "404s and sets X-Cascade header when no route satisfies the request" do + mock_app { + get('/foo') { } + } + get '/bar' + assert_equal 404, status + assert_equal 'pass', response.headers['X-Cascade'] + end + it "overrides the content-type in error handlers" do mock_app { before { content_type 'text/plain' } @@ -462,6 +471,23 @@ class RoutingTest < Test::Unit::TestCase assert not_found? end + it "transitions to 404 and sets X-Cascade header when passed and no subsequent route matches" do + mock_app { + get '/:foo' do + pass + 'Hello Foo' + end + + get '/bar' do + 'Hello Bar' + end + } + + get '/foo' + assert not_found? + assert_equal 'pass', response.headers['X-Cascade'] + end + it "uses optional block passed to pass as route block if no other route is found" do mock_app { get "/" do