require_relative "../spec_helper"
describe "exception_page plugin" do
def ep_app(&block)
app(:exception_page) do |r|
raise "foo" rescue block ? instance_exec($!, &block) : exception_page($!)
end
end
def req(path = '/', headers={})
if path.is_a?(Hash)
super(path.merge('rack.input'=>StringIO.new))
else
super(path, headers.merge('rack.input'=>StringIO.new))
end
end
it "returns HTML page with exception information if text/html is accepted" do
ep_app
s, h, body = req('HTTP_ACCEPT'=>'text/html')
s.must_equal 200
h['Content-Type'].must_equal 'text/html'
body = body.join
body.must_include "
RuntimeError at /"
body.must_include "RuntimeError at /
"
body.must_include "foo
"
body.must_include __FILE__
body.must_include "No GET data"
body.must_include "No POST data"
body.must_include "No cookie data"
body.must_include "Rack ENV"
body.must_include "HTTP_ACCEPT"
body.must_include "text/html"
body.must_include "table td.code"
body.must_include "function toggle()"
body.wont_include "\"/exception_page.css\""
body.wont_include "\"/exception_page.js\""
size = body.size
ep_app{|e| exception_page(e, :context=>10)}
body('HTTP_ACCEPT'=>'text/html').size.must_be :>, size
ep_app{|e| exception_page(e, :assets=>true, :context=>0)}
body = body('HTTP_ACCEPT'=>'text/html')
body.wont_include "table td.code"
body.wont_include "function toggle()"
body.must_include "\"/exception_page.css\""
body.must_include "\"/exception_page.js\""
ep_app{|e| exception_page(e, :assets=>"/static", :context=>0)}
body = body('HTTP_ACCEPT'=>'text/html')
body.wont_include "table td.code"
body.wont_include "function toggle()"
body.must_include "\"/static/exception_page.css\""
body.must_include "\"/static/exception_page.js\""
ep_app{|e| exception_page(e, :css_file=>"/foo.css", :context=>0)}
body = body('HTTP_ACCEPT'=>'text/html')
body.wont_include "table td.code"
body.must_include "function toggle()"
body.must_include "\"/foo.css\""
ep_app{|e| exception_page(e, :js_file=>"/foo.js", :context=>0)}
body = body('HTTP_ACCEPT'=>'text/html')
body.must_include "table td.code"
body.wont_include "function toggle()"
body.must_include "\"/foo.js\""
ep_app{|e| exception_page(e, :assets=>false, :context=>0)}
body = body('HTTP_ACCEPT'=>'text/html')
body.wont_include "table td.code"
body.wont_include "function toggle()"
body.wont_include "\"/exception_page.css\""
body.wont_include "\"/exception_page.js\""
ep_app{|e| exception_page(e, :assets=>false, :css_file=>"/foo.css", :context=>0)}
body = body('HTTP_ACCEPT'=>'text/html')
body.wont_include "table td.code"
body.wont_include "function toggle()"
body.must_include "\"/foo.css\""
ep_app{|e| exception_page(e, :assets=>false, :js_file=>"/foo.js", :context=>0)}
body = body('HTTP_ACCEPT'=>'text/html')
body.wont_include "table td.code"
body.wont_include "function toggle()"
body.must_include "\"/foo.js\""
ep_app{|e| exception_page(e, :css_file=>false, :context=>0)}
body = body('HTTP_ACCEPT'=>'text/html')
body.wont_include "table td.code"
body.must_include "function toggle()"
body.wont_include "\"/exception_page.css\""
body.wont_include "\"/exception_page.js\""
ep_app{|e| exception_page(e, :js_file=>false, :context=>0)}
body = body('HTTP_ACCEPT'=>'text/html')
body.must_include "table td.code"
body.wont_include "function toggle()"
body.wont_include "\"/exception_page.css\""
body.wont_include "\"/exception_page.js\""
end
it "returns plain text page with exception information if text/html is not accepted" do
ep_app
s, h, body = req
s.must_equal 200
h['Content-Type'].must_equal 'text/plain'
body = body.join
first, *bt = body.split("\n")
first.must_equal "RuntimeError: foo"
bt.first.must_include __FILE__
end
it "returns JSON with exception information if :json information is used" do
ep_app{|e| exception_page(e, :json=>true)}
@app.plugin :json
s, h, body = req
s.must_equal 200
h['Content-Type'].must_equal 'application/json'
hash = JSON.parse(body.join)
bt = hash["exception"].delete("backtrace")
hash.must_equal("exception"=>{"class"=>"RuntimeError", "message"=>"foo"})
bt.must_be_kind_of Array
bt.each{|line| line.must_be_kind_of String}
end
it "should handle backtrace lines in unexpected forms" do
ep_app do |e|
e.backtrace.first.upcase!
e.backtrace[-1] = ''
exception_page(e)
end
body = body('HTTP_ACCEPT'=>'text/html')
body.must_include "RuntimeError: foo"
body.must_include __FILE__
body.wont_include 'id="c0"'
end
it "should serve exception page assets" do
app(:exception_page) do |r|
r.exception_page_assets
end
s, h, b = req('/exception_page.css')
s.must_equal 200
h['Content-Type'].must_equal 'text/css'
b.join.must_equal Roda::RodaPlugins::ExceptionPage.css
s, h, b = req('/exception_page.js')
s.must_equal 200
h['Content-Type'].must_equal 'application/javascript'
b.join.must_equal Roda::RodaPlugins::ExceptionPage.js
end
end