mirror of
https://github.com/sinatra/sinatra
synced 2023-03-27 23:18:01 -04:00
Merge remote-tracking branch 'upstream/master'
This commit is contained in:
commit
ba01aa8694
9 changed files with 66 additions and 24 deletions
16
.travis.yml
Normal file
16
.travis.yml
Normal file
|
@ -0,0 +1,16 @@
|
|||
rvm:
|
||||
- 1.8.7
|
||||
- 1.9.2
|
||||
- 1.9.3
|
||||
- rbx
|
||||
- rbx-2.0
|
||||
# - jruby
|
||||
- ruby-head
|
||||
env:
|
||||
- "rack=1.3.0"
|
||||
- "rack=master"
|
||||
- "tilt=1.3.2"
|
||||
- "tilt=master"
|
||||
notifications:
|
||||
recipients:
|
||||
- k.haase@finn.de
|
6
Gemfile
6
Gemfile
|
@ -38,7 +38,11 @@ gem 'kramdown'
|
|||
gem 'maruku'
|
||||
gem 'creole'
|
||||
|
||||
gem 'nokogiri' if RUBY_ENGINE != 'maglev'
|
||||
if RUBY_ENGINE == 'jruby'
|
||||
gem 'nokogiri', '!= 1.5.0'
|
||||
elsif RUBY_ENGINE != 'maglev'
|
||||
gem 'nokogiri'
|
||||
end
|
||||
|
||||
unless RUBY_ENGINE == 'jruby' && JRUBY_VERSION < "1.6.1"
|
||||
# C extensions
|
||||
|
|
|
@ -100,6 +100,13 @@ O con un parámetro de bloque:
|
|||
"Hola, #{c}!"
|
||||
end
|
||||
|
||||
Los patrones de ruta pueden contener parámetros opcionales:
|
||||
|
||||
get '/posts.?:formato?' do
|
||||
# coincide con "GET /posts" y además admite cualquier extensión, por
|
||||
# ejemplo, "GET /posts.json", "GET /posts.xml", etc.
|
||||
end
|
||||
|
||||
=== Condiciones
|
||||
|
||||
Las rutas pueden incluir una variedad de condiciones de selección, como por
|
||||
|
@ -431,7 +438,7 @@ layout distinto al de la plantilla pasando la opción <tt>:layout_engine</tt>.
|
|||
|
||||
Dependencias:: {rdoc}[http://rdoc.rubyforge.org/]
|
||||
Extensiones de Archivo:: <tt>.rdoc</tt>
|
||||
Ejemplo:: <tt>textile :LEEME, :layout_engine => :erb</tt>
|
||||
Ejemplo:: <tt>rdoc :LEEME, :layout_engine => :erb</tt>
|
||||
|
||||
No es posible llamar métodos desde rdoc, ni pasarle locales. Por lo tanto,
|
||||
generalmente vas a usarlo en combinación con otro motor de renderizado:
|
||||
|
@ -1850,3 +1857,4 @@ siguiendo las especificaciones SemVer y SemVerTag.
|
|||
{última versión liberada}[http://rubydoc.info/gems/sinatra] o para la
|
||||
{rama de desarrollo actual}[http://rubydoc.info/github/sinatra/sinatra]
|
||||
en http://rubydoc.info/
|
||||
* {Servidor de IC}[http://ci.rkh.im/view/Sinatra/]
|
||||
|
|
|
@ -98,6 +98,12 @@ Or with a block parameter:
|
|||
"Hello, #{c}!"
|
||||
end
|
||||
|
||||
Route patterns may have optional parameters:
|
||||
|
||||
get '/posts.?:format?' do
|
||||
# matches "GET /posts" and any extension "GET /posts.json", "GET /posts.xml" etc.
|
||||
end
|
||||
|
||||
=== Conditions
|
||||
|
||||
Routes may include a variety of matching conditions, such as the user agent:
|
||||
|
|
|
@ -700,12 +700,12 @@ module Sinatra
|
|||
# Revert params afterwards.
|
||||
#
|
||||
# Returns pass block.
|
||||
def process_route(pattern, keys, conditions, block = nil, values = nil)
|
||||
def process_route(pattern, keys, conditions, block = nil, values = [])
|
||||
@original_params ||= @params
|
||||
route = @request.path_info
|
||||
route = '/' if route.empty? and not settings.empty_path_info?
|
||||
if match = pattern.match(route)
|
||||
values = match.captures.to_a.map { |v| force_encoding URI.decode(v) if v }
|
||||
values += match.captures.to_a.map { |v| force_encoding URI.decode(v) if v }
|
||||
params =
|
||||
if keys.any?
|
||||
keys.zip(values).inject({}) do |hash,(k,v)|
|
||||
|
@ -801,29 +801,33 @@ module Sinatra
|
|||
def handle_exception!(boom)
|
||||
@env['sinatra.error'] = boom
|
||||
status boom.respond_to?(:code) ? Integer(boom.code) : 500
|
||||
dump_errors! boom if settings.dump_errors? and server_error?
|
||||
raise boom if settings.show_exceptions? and settings.show_exceptions != :after_handler
|
||||
|
||||
if server_error?
|
||||
dump_errors! boom if settings.dump_errors?
|
||||
raise boom if settings.show_exceptions? and settings.show_exceptions != :after_handler
|
||||
end
|
||||
|
||||
if not_found?
|
||||
headers['X-Cascade'] = 'pass'
|
||||
body '<h1>Not Found</h1>'
|
||||
end
|
||||
|
||||
res = error_block!(boom.class) || error_block!(status)
|
||||
res = error_block!(boom.class, boom) || error_block!(status, boom)
|
||||
return res if res or not server_error?
|
||||
raise boom if settings.raise_errors? or settings.show_exceptions?
|
||||
error_block! Exception
|
||||
error_block! Exception, boom
|
||||
end
|
||||
|
||||
# Find an custom error block for the key(s) specified.
|
||||
def error_block!(key)
|
||||
def error_block!(key, *block_params)
|
||||
base = settings
|
||||
while base.respond_to?(:errors)
|
||||
next base = base.superclass unless args = base.errors[key]
|
||||
args += [block_params]
|
||||
return process_route(*args)
|
||||
end
|
||||
return false unless key.respond_to? :superclass and key.superclass < Exception
|
||||
error_block! key.superclass
|
||||
error_block!(key.superclass, *block_params)
|
||||
end
|
||||
|
||||
def dump_errors!(boom)
|
||||
|
|
|
@ -252,7 +252,7 @@ TEMPLATE = <<-HTML # :nodoc:
|
|||
|
||||
<div id="get">
|
||||
<h3 id="get-info">GET</h3>
|
||||
<% unless req.GET.empty? %>
|
||||
<% if req.GET and not req.GET.empty? %>
|
||||
<table class="req">
|
||||
<tr>
|
||||
<th>Variable</th>
|
||||
|
@ -273,7 +273,7 @@ TEMPLATE = <<-HTML # :nodoc:
|
|||
|
||||
<div id="post">
|
||||
<h3 id="post-info">POST</h3>
|
||||
<% unless req.POST.empty? %>
|
||||
<% if req.POST and not req.POST.empty? %>
|
||||
<table class="req">
|
||||
<tr>
|
||||
<th>Variable</th>
|
||||
|
|
|
@ -2,8 +2,8 @@ $LOAD_PATH.unshift File.expand_path('../lib', __FILE__)
|
|||
require 'sinatra/version'
|
||||
|
||||
Gem::Specification.new 'sinatra', Sinatra::VERSION do |s|
|
||||
s.description = "Classy web-development dressed in a DSL"
|
||||
s.summary = s.description
|
||||
s.description = "Sinatra is a DSL for quickly creating web applications in Ruby with minimal effort."
|
||||
s.summary = "Classy web-development dressed in a DSL"
|
||||
s.authors = ["Blake Mizerany", "Ryan Tomayko", "Simon Rozet", "Konstantin Haase"]
|
||||
s.email = "sinatrarb@googlegroups.com"
|
||||
s.homepage = "http://www.sinatrarb.com/"
|
||||
|
|
|
@ -29,6 +29,15 @@ class MappedErrorTest < Test::Unit::TestCase
|
|||
assert_equal 'Foo!', body
|
||||
end
|
||||
|
||||
it 'passes the exception object to the error handler' do
|
||||
mock_app do
|
||||
set :raise_errors, false
|
||||
error(FooError) { |e| assert_equal(FooError, e.class) }
|
||||
get('/') { raise FooError }
|
||||
end
|
||||
get('/')
|
||||
end
|
||||
|
||||
it 'uses the Exception handler if no matching handler found' do
|
||||
mock_app {
|
||||
set :raise_errors, false
|
||||
|
@ -112,12 +121,7 @@ class MappedErrorTest < Test::Unit::TestCase
|
|||
end
|
||||
|
||||
it "never raises Sinatra::NotFound beyond the application" do
|
||||
mock_app {
|
||||
set :raise_errors, true
|
||||
get '/' do
|
||||
raise Sinatra::NotFound
|
||||
end
|
||||
}
|
||||
mock_app(Sinatra::Application) { get('/') { raise Sinatra::NotFound }}
|
||||
assert_nothing_raised { get '/' }
|
||||
assert_equal 404, status
|
||||
end
|
||||
|
|
|
@ -54,7 +54,7 @@ class SlimTest < Test::Unit::TestCase
|
|||
it "passes slim options to the slim engine" do
|
||||
mock_app {
|
||||
get '/' do
|
||||
slim "! doctype html\nh1 Hello World", :format => :html4
|
||||
slim "doctype html\nh1 Hello World", :format => :html4
|
||||
end
|
||||
}
|
||||
get '/'
|
||||
|
@ -66,7 +66,7 @@ class SlimTest < Test::Unit::TestCase
|
|||
mock_app {
|
||||
set :slim, {:format => :html4}
|
||||
get '/' do
|
||||
slim "! doctype html\nh1 Hello World"
|
||||
slim "doctype html\nh1 Hello World"
|
||||
end
|
||||
}
|
||||
get '/'
|
||||
|
@ -78,10 +78,10 @@ class SlimTest < Test::Unit::TestCase
|
|||
mock_app {
|
||||
set :slim, {:format => :html4}
|
||||
get '/' do
|
||||
slim "! doctype html\nh1.header Hello World"
|
||||
slim "doctype html\nh1.header Hello World"
|
||||
end
|
||||
get '/html5' do
|
||||
slim "! doctype html\nh1.header Hello World", :format => :html5
|
||||
slim "doctype html\nh1.header Hello World", :format => :html5
|
||||
end
|
||||
}
|
||||
get '/'
|
||||
|
|
Loading…
Reference in a new issue