mirror of
https://github.com/sinatra/sinatra
synced 2023-03-27 23:18:01 -04:00
starting
This commit is contained in:
parent
68f364e60c
commit
5e5f0c021a
26 changed files with 0 additions and 1437 deletions
|
@ -1,83 +0,0 @@
|
||||||
require "rubygems"
|
|
||||||
|
|
||||||
if ENV['SWIFT']
|
|
||||||
require 'swiftcore/swiftiplied_mongrel'
|
|
||||||
puts "Using Swiftiplied Mongrel"
|
|
||||||
elsif ENV['EVENT']
|
|
||||||
require 'swiftcore/evented_mongrel'
|
|
||||||
puts "Using Evented Mongrel"
|
|
||||||
end
|
|
||||||
|
|
||||||
require "rack"
|
|
||||||
|
|
||||||
require File.dirname(__FILE__) + '/sinatra/application'
|
|
||||||
require File.dirname(__FILE__) + '/sinatra/event_context'
|
|
||||||
require File.dirname(__FILE__) + '/sinatra/route'
|
|
||||||
require File.dirname(__FILE__) + '/sinatra/error'
|
|
||||||
require File.dirname(__FILE__) + '/sinatra/mime_types'
|
|
||||||
require File.dirname(__FILE__) + '/sinatra/core_ext'
|
|
||||||
require File.dirname(__FILE__) + '/sinatra/halt_results'
|
|
||||||
require File.dirname(__FILE__) + '/sinatra/logger'
|
|
||||||
|
|
||||||
def get(*paths, &b)
|
|
||||||
options = Hash === paths.last ? paths.pop : {}
|
|
||||||
paths.map { |path| Sinatra.define_route(:get, path, options, &b) }
|
|
||||||
end
|
|
||||||
|
|
||||||
def post(*paths, &b)
|
|
||||||
options = Hash === paths.last ? paths.pop : {}
|
|
||||||
paths.map { |path| Sinatra.define_route(:post, path, options, &b) }
|
|
||||||
end
|
|
||||||
|
|
||||||
def put(*paths, &b)
|
|
||||||
options = Hash === paths.last ? paths.pop : {}
|
|
||||||
paths.map { |path| Sinatra.define_route(:put, path, options, &b) }
|
|
||||||
end
|
|
||||||
|
|
||||||
def delete(*paths, &b)
|
|
||||||
options = Hash === paths.last ? paths.pop : {}
|
|
||||||
paths.map { |path| Sinatra.define_route(:delete, path, options, &b) }
|
|
||||||
end
|
|
||||||
|
|
||||||
def error(*codes, &b)
|
|
||||||
raise 'You must specify a block to assciate with an error' if b.nil?
|
|
||||||
codes.each { |code| Sinatra.define_error(code, &b) }
|
|
||||||
end
|
|
||||||
|
|
||||||
def before(*groups, &b)
|
|
||||||
groups = [:all] if groups.empty?
|
|
||||||
groups.each { |group| Sinatra.define_filter(:before, group, &b) }
|
|
||||||
end
|
|
||||||
|
|
||||||
def after(*groups, &b)
|
|
||||||
groups = [:all] if groups.empty?
|
|
||||||
groups.each { |group| Sinatra.define_filter(:after, group, &b) }
|
|
||||||
end
|
|
||||||
|
|
||||||
def mime_type(content_type, *exts)
|
|
||||||
exts.each { |ext| Sinatra::MIME_TYPES.merge(ext.to_s, content_type) }
|
|
||||||
end
|
|
||||||
|
|
||||||
def helpers(&b)
|
|
||||||
Sinatra::EventContext.class_eval(&b)
|
|
||||||
end
|
|
||||||
|
|
||||||
def configures(*envs)
|
|
||||||
return if Sinatra.config[:reloading]
|
|
||||||
yield if (envs.include?(Sinatra.config[:env]) || envs.empty?)
|
|
||||||
end
|
|
||||||
alias :configure :configures
|
|
||||||
|
|
||||||
Sinatra.setup_default_events!
|
|
||||||
|
|
||||||
at_exit do
|
|
||||||
raise $! if $!
|
|
||||||
Sinatra.setup_logger
|
|
||||||
|
|
||||||
#TODO: Move this into command line options
|
|
||||||
if ARGV.include?('-i')
|
|
||||||
require File.dirname(__FILE__) + '/sinatra/irb'
|
|
||||||
end
|
|
||||||
|
|
||||||
Sinatra.run if Sinatra.config[:run]
|
|
||||||
end
|
|
|
@ -1,218 +0,0 @@
|
||||||
module Sinatra
|
|
||||||
extend self
|
|
||||||
|
|
||||||
def method_missing(name, *args, &b)
|
|
||||||
Application.send(name, *args, &b)
|
|
||||||
end
|
|
||||||
|
|
||||||
module Application
|
|
||||||
extend self
|
|
||||||
|
|
||||||
attr_accessor :logger
|
|
||||||
|
|
||||||
def run
|
|
||||||
|
|
||||||
begin
|
|
||||||
puts "== Sinatra has taken the stage on port #{Sinatra.config[:port]} for #{Sinatra.config[:env]}"
|
|
||||||
require 'pp'
|
|
||||||
Rack::Handler::Mongrel.run(Sinatra, :Port => Sinatra.config[:port]) do |server|
|
|
||||||
trap(:INT) do
|
|
||||||
server.stop
|
|
||||||
puts "\n== Sinatra has ended his set (crowd applauds)"
|
|
||||||
end
|
|
||||||
end
|
|
||||||
rescue Errno::EADDRINUSE => e
|
|
||||||
puts "== Someone is already performing on port #{Sinatra.config[:port]}!"
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
def setup_logger
|
|
||||||
self.logger = Sinatra::Logger.new(
|
|
||||||
config[:root] + "/#{Sinatra.config[:env]}.log"
|
|
||||||
)
|
|
||||||
end
|
|
||||||
|
|
||||||
def setup_default_events!
|
|
||||||
error 500 do
|
|
||||||
"<h2>#{$!.message}</h2>#{$!.backtrace.join("<br/>")}"
|
|
||||||
end
|
|
||||||
|
|
||||||
error 404 do
|
|
||||||
"<h1>Not Found</h1>"
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
def request_types
|
|
||||||
@request_types ||= [:get, :put, :post, :delete]
|
|
||||||
end
|
|
||||||
|
|
||||||
def routes
|
|
||||||
@routes ||= Hash.new do |hash, key|
|
|
||||||
hash[key] = [] if request_types.include?(key)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
def filters
|
|
||||||
unless @filters
|
|
||||||
@filters = Hash.new do |hash, key|
|
|
||||||
hash[key] = Hash.new { |hash, key| hash[key] = [] }
|
|
||||||
end
|
|
||||||
end
|
|
||||||
@filters
|
|
||||||
end
|
|
||||||
|
|
||||||
def config
|
|
||||||
@config ||= default_config.dup
|
|
||||||
end
|
|
||||||
|
|
||||||
def config=(c)
|
|
||||||
@config = c
|
|
||||||
end
|
|
||||||
|
|
||||||
def development?
|
|
||||||
config[:env] == :development
|
|
||||||
end
|
|
||||||
|
|
||||||
def default_config
|
|
||||||
@default_config ||= {
|
|
||||||
:run => true,
|
|
||||||
:port => 4567,
|
|
||||||
:raise_errors => false,
|
|
||||||
:env => :development,
|
|
||||||
:root => Dir.pwd,
|
|
||||||
:default_static_mime_type => 'text/plain',
|
|
||||||
:default_params => { :format => 'html' }
|
|
||||||
}
|
|
||||||
end
|
|
||||||
|
|
||||||
def determine_route(verb, path)
|
|
||||||
routes[verb].eject { |r| r.match(path) } || routes[404]
|
|
||||||
end
|
|
||||||
|
|
||||||
def content_type_for(path)
|
|
||||||
ext = File.extname(path)[1..-1]
|
|
||||||
Sinatra.mime_types[ext] || config[:default_static_mime_type]
|
|
||||||
end
|
|
||||||
|
|
||||||
def serve_static_file(path)
|
|
||||||
path = Sinatra.config[:root] + '/public' + path
|
|
||||||
if File.file?(path)
|
|
||||||
headers = {
|
|
||||||
'Content-Type' => Array(content_type_for(path)),
|
|
||||||
'Content-Length' => Array(File.size(path))
|
|
||||||
}
|
|
||||||
[200, headers, File.read(path)]
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
def call(env)
|
|
||||||
|
|
||||||
reload! if Sinatra.development?
|
|
||||||
|
|
||||||
time = Time.now
|
|
||||||
|
|
||||||
request = Rack::Request.new(env)
|
|
||||||
|
|
||||||
if found = serve_static_file(request.path_info)
|
|
||||||
log_request_and_response(time, request, Rack::Response.new(found))
|
|
||||||
return found
|
|
||||||
end
|
|
||||||
|
|
||||||
response = Rack::Response.new
|
|
||||||
route = determine_route(
|
|
||||||
request.request_method.downcase.to_sym,
|
|
||||||
request.path_info
|
|
||||||
)
|
|
||||||
context = EventContext.new(request, response, route.params)
|
|
||||||
context.status = nil
|
|
||||||
begin
|
|
||||||
context = handle_with_filters(route.groups, context, &route.block)
|
|
||||||
context.status ||= route.default_status
|
|
||||||
rescue => e
|
|
||||||
raise e if config[:raise_errors]
|
|
||||||
route = Sinatra.routes[500]
|
|
||||||
context.status 500
|
|
||||||
context.body Array(context.instance_eval(&route.block))
|
|
||||||
ensure
|
|
||||||
log_request_and_response(time, request, response)
|
|
||||||
logger.flush
|
|
||||||
end
|
|
||||||
|
|
||||||
context.finish
|
|
||||||
end
|
|
||||||
|
|
||||||
def define_route(verb, path, options = {}, &b)
|
|
||||||
routes[verb] << route = Route.new(path, Array(options[:groups]), &b)
|
|
||||||
route
|
|
||||||
end
|
|
||||||
|
|
||||||
def define_error(code, &b)
|
|
||||||
routes[code] = Error.new(code, &b)
|
|
||||||
end
|
|
||||||
|
|
||||||
def define_filter(type, group, &b)
|
|
||||||
filters[type][group] << b
|
|
||||||
end
|
|
||||||
|
|
||||||
def reset!
|
|
||||||
self.config = nil
|
|
||||||
routes.clear
|
|
||||||
filters.clear
|
|
||||||
setup_default_events!
|
|
||||||
end
|
|
||||||
|
|
||||||
def reload!
|
|
||||||
reset!
|
|
||||||
self.config[:reloading] = true
|
|
||||||
load $0
|
|
||||||
self.config[:reloading] = false
|
|
||||||
end
|
|
||||||
|
|
||||||
protected
|
|
||||||
|
|
||||||
def log_request_and_response(time, request, response)
|
|
||||||
now = Time.now
|
|
||||||
|
|
||||||
# Common Log Format: http://httpd.apache.org/docs/1.3/logs.html#common
|
|
||||||
# lilith.local - - [07/Aug/2006 23:58:02] "GET / HTTP/1.1" 500 -
|
|
||||||
# %{%s - %s [%s] "%s %s%s %s" %d %s\n} %
|
|
||||||
logger.info %{%s - %s [%s] "%s %s%s %s" %d %s %0.4f\n} %
|
|
||||||
[
|
|
||||||
request.env["REMOTE_ADDR"] || "-",
|
|
||||||
request.env["REMOTE_USER"] || "-",
|
|
||||||
now.strftime("%d/%b/%Y %H:%M:%S"),
|
|
||||||
request.env["REQUEST_METHOD"],
|
|
||||||
request.env["PATH_INFO"],
|
|
||||||
request.env["QUERY_STRING"].empty? ?
|
|
||||||
"" :
|
|
||||||
"?" + request.env["QUERY_STRING"],
|
|
||||||
request.env["HTTP_VERSION"],
|
|
||||||
response.status.to_s[0..3].to_i,
|
|
||||||
(response.body.length.zero? ? "-" : response.body.length.to_s),
|
|
||||||
now - time
|
|
||||||
]
|
|
||||||
end
|
|
||||||
|
|
||||||
def handle_with_filters(groups, cx, &b)
|
|
||||||
caught = catch(:halt) do
|
|
||||||
filters_for(:before, groups).each { |x| cx.instance_eval(&x) }
|
|
||||||
[:complete, b]
|
|
||||||
end
|
|
||||||
caught = catch(:halt) do
|
|
||||||
caught.to_result(cx)
|
|
||||||
end
|
|
||||||
result = caught.to_result(cx) if caught
|
|
||||||
filters_for(:after, groups).each { |x| cx.instance_eval(&x) }
|
|
||||||
cx.body Array(result.to_s)
|
|
||||||
cx
|
|
||||||
end
|
|
||||||
|
|
||||||
def filters_for(type, groups)
|
|
||||||
filters[type][:all] + groups.inject([]) do |m, g|
|
|
||||||
m + filters[type][g]
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,58 +0,0 @@
|
||||||
def silence_warnings
|
|
||||||
old_verbose, $VERBOSE = $VERBOSE, nil
|
|
||||||
yield
|
|
||||||
ensure
|
|
||||||
$VERBOSE = old_verbose
|
|
||||||
end
|
|
||||||
|
|
||||||
class String
|
|
||||||
def to_param
|
|
||||||
URI.escape(self)
|
|
||||||
end
|
|
||||||
|
|
||||||
def from_param
|
|
||||||
URI.unescape(self)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
class Hash
|
|
||||||
def to_params
|
|
||||||
map { |k,v| "#{k}=#{URI.escape(v)}" }.join('&')
|
|
||||||
end
|
|
||||||
|
|
||||||
def symbolize_keys
|
|
||||||
self.inject({}) { |h,(k,v)| h[k.to_sym] = v; h }
|
|
||||||
end
|
|
||||||
|
|
||||||
def pass(*keys)
|
|
||||||
reject { |k,v| !keys.include?(k) }
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
class Symbol
|
|
||||||
def to_proc
|
|
||||||
Proc.new { |*args| args.shift.__send__(self, *args) }
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
class Array
|
|
||||||
def to_hash
|
|
||||||
self.inject({}) { |h, (k, v)| h[k] = v; h }
|
|
||||||
end
|
|
||||||
|
|
||||||
def to_proc
|
|
||||||
Proc.new { |*args| args.shift.__send__(self[0], args + self[1..-1]) }
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
class Proc
|
|
||||||
def block
|
|
||||||
self
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
module Enumerable
|
|
||||||
def eject(&block)
|
|
||||||
find { |e| result = block[e] and break result }
|
|
||||||
end
|
|
||||||
end
|
|
|
@ -1,17 +0,0 @@
|
||||||
class Error
|
|
||||||
|
|
||||||
attr_reader :block
|
|
||||||
|
|
||||||
def initialize(code, &b)
|
|
||||||
@code, @block = code, b
|
|
||||||
end
|
|
||||||
|
|
||||||
def default_status
|
|
||||||
@code
|
|
||||||
end
|
|
||||||
|
|
||||||
def params; {}; end
|
|
||||||
|
|
||||||
def groups; []; end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,40 +0,0 @@
|
||||||
class Sinatra::EventContext
|
|
||||||
|
|
||||||
attr_reader :request, :response, :route_params
|
|
||||||
|
|
||||||
def logger
|
|
||||||
Sinatra.logger
|
|
||||||
end
|
|
||||||
|
|
||||||
def initialize(request, response, route_params)
|
|
||||||
@request, @response, @route_params =
|
|
||||||
request, response, route_params
|
|
||||||
end
|
|
||||||
|
|
||||||
def params
|
|
||||||
@params ||= request.params.merge(route_params).symbolize_keys
|
|
||||||
end
|
|
||||||
|
|
||||||
def complete(b)
|
|
||||||
self.instance_eval(&b)
|
|
||||||
end
|
|
||||||
|
|
||||||
# redirect to another url It can be like /foo/bar
|
|
||||||
# for redirecting within your same app. Or it can
|
|
||||||
# be a fully qualified url to another site.
|
|
||||||
def redirect(url)
|
|
||||||
logger.info "Redirecting to: #{url}"
|
|
||||||
status(302)
|
|
||||||
headers.merge!('Location' => url)
|
|
||||||
return ''
|
|
||||||
end
|
|
||||||
|
|
||||||
def method_missing(name, *args)
|
|
||||||
if args.size == 1 && response.respond_to?("#{name}=")
|
|
||||||
response.send("#{name}=", args.first)
|
|
||||||
else
|
|
||||||
response.send(name, *args)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,30 +0,0 @@
|
||||||
class Proc
|
|
||||||
def to_result(cx, *args)
|
|
||||||
cx.instance_eval(&self)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
class String
|
|
||||||
def to_result(cx, *args)
|
|
||||||
cx.body self
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
class Array
|
|
||||||
def to_result(cx, *args)
|
|
||||||
self.shift.to_result(cx, *self)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
class Symbol
|
|
||||||
def to_result(cx, *args)
|
|
||||||
cx.send(self, *args)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
class Fixnum
|
|
||||||
def to_result(cx, *args)
|
|
||||||
cx.status self
|
|
||||||
cx.body args.first
|
|
||||||
end
|
|
||||||
end
|
|
|
@ -1,45 +0,0 @@
|
||||||
require File.dirname(__FILE__) + '/test/methods'
|
|
||||||
|
|
||||||
Object.send(:include, Sinatra::Test::Methods) # added to allow post_to in console
|
|
||||||
|
|
||||||
Object.class_eval do
|
|
||||||
|
|
||||||
# Reload all Sinatra and App specific files
|
|
||||||
def reload!
|
|
||||||
Sinatra.reload!
|
|
||||||
end
|
|
||||||
|
|
||||||
# Show the +body+ with result info in your text editor!!! Great Job!
|
|
||||||
def show!(editor = nil)
|
|
||||||
editor = editor || ENV['EDITOR']
|
|
||||||
IO.popen(editor, 'w') do |f|
|
|
||||||
f.puts "<!--"
|
|
||||||
f.puts result_info
|
|
||||||
f.puts "-->"
|
|
||||||
f.puts
|
|
||||||
f.puts body
|
|
||||||
end
|
|
||||||
nil
|
|
||||||
end
|
|
||||||
alias :mate :show!
|
|
||||||
|
|
||||||
def result_info #:nodoc:
|
|
||||||
info = <<-end_info
|
|
||||||
# Status: #{status}
|
|
||||||
# Headers: #{headers.inspect}
|
|
||||||
end_info
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
ARGV.clear # Avoid passing args to IRB
|
|
||||||
require 'irb'
|
|
||||||
require 'irb/completion'
|
|
||||||
def exit
|
|
||||||
exit!
|
|
||||||
end
|
|
||||||
if File.exists? ".irbrc"
|
|
||||||
ENV['IRBRC'] = ".irbrc"
|
|
||||||
end
|
|
||||||
IRB.start
|
|
||||||
exit!
|
|
|
@ -1,75 +0,0 @@
|
||||||
# Adapted from Merb greatness
|
|
||||||
|
|
||||||
module Sinatra
|
|
||||||
|
|
||||||
class Logger
|
|
||||||
module Severity
|
|
||||||
DEBUG = 0
|
|
||||||
INFO = 1
|
|
||||||
WARN = 2
|
|
||||||
ERROR = 3
|
|
||||||
FATAL = 4
|
|
||||||
UNKNOWN = 5
|
|
||||||
end
|
|
||||||
include Severity
|
|
||||||
|
|
||||||
attr_accessor :level
|
|
||||||
attr_reader :buffer
|
|
||||||
|
|
||||||
def initialize(log, level = DEBUG)
|
|
||||||
@level = level
|
|
||||||
@buffer = []
|
|
||||||
if log.respond_to?(:write)
|
|
||||||
@log = log
|
|
||||||
elsif File.exist?(log)
|
|
||||||
@log = open(log, (File::WRONLY | File::APPEND))
|
|
||||||
@log.sync = true
|
|
||||||
else
|
|
||||||
@log = open(log, (File::WRONLY | File::APPEND | File::CREAT))
|
|
||||||
@log.sync = true
|
|
||||||
@log.write("# Logfile created on %s\n" % [Time.now.to_s])
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
def flush
|
|
||||||
unless @buffer.size == 0
|
|
||||||
@aio ||= !Sinatra.config.to_s.match(/development|test/) # && !RUBY_PLATFORM.match(/java|mswin/) &&
|
|
||||||
@log.respond_to?(:write_nonblock)
|
|
||||||
if @aio
|
|
||||||
@log.write_nonblock(@buffer.slice!(0..-1).to_s)
|
|
||||||
else
|
|
||||||
@log.write(@buffer.slice!(0..-1).to_s)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
def close
|
|
||||||
flush
|
|
||||||
@log.close if @log.respond_to?(:close)
|
|
||||||
@log = nil
|
|
||||||
end
|
|
||||||
|
|
||||||
def add(severity, message = nil, progname = nil, &block)
|
|
||||||
return if @level > severity
|
|
||||||
message = (message || (block && block.call) || progname).to_s
|
|
||||||
# If a newline is necessary then create a new message ending with a newline.
|
|
||||||
# Ensures that the original message is not mutated.
|
|
||||||
message = "#{message}\n" unless message[-1] == ?\n
|
|
||||||
@buffer << message
|
|
||||||
message
|
|
||||||
end
|
|
||||||
|
|
||||||
Severity.constants.each do |severity|
|
|
||||||
class_eval <<-EOT
|
|
||||||
def #{severity.downcase}(message = nil, progname = nil, &block)
|
|
||||||
add(#{severity}, message, progname, &block)
|
|
||||||
end
|
|
||||||
|
|
||||||
def #{severity.downcase}?
|
|
||||||
#{severity} >= @level
|
|
||||||
end
|
|
||||||
EOT
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
||||||
end
|
|
|
@ -1,256 +0,0 @@
|
||||||
module Sinatra
|
|
||||||
|
|
||||||
def mime_types
|
|
||||||
|
|
||||||
@default_mime_types ||= {
|
|
||||||
"csh"=>"application/x-csh",
|
|
||||||
"x_t"=>"model/vnd.parasolid.transmit.text",
|
|
||||||
"ksp"=>"application/vnd.kde.kspread",
|
|
||||||
"fsc"=>"application/vnd.fsc.weblaunch",
|
|
||||||
"vcs"=>"text/x-vcalendar",
|
|
||||||
"hvs"=>"application/vnd.yamaha.hv-script",
|
|
||||||
"seml"=>"application/vnd.sealed.eml",
|
|
||||||
"movie"=>"video/x-sgi-movie",
|
|
||||||
"plt"=>"application/vnd.hp-HPGL",
|
|
||||||
"wav"=>"audio/x-wav",
|
|
||||||
"3gpp"=>"audio/3gpp",
|
|
||||||
"eol"=>"audio/vnd.digital-winds",
|
|
||||||
"rtf"=>"application/rtf",
|
|
||||||
"kfo"=>"application/vnd.kde.kformula",
|
|
||||||
"rdf"=>"application/rdf+xml",
|
|
||||||
"rgb"=>"image/x-rgb",
|
|
||||||
"wpd"=>"application/vnd.wordperfect",
|
|
||||||
"sit"=>"application/x-stuffit",
|
|
||||||
"ogg"=>"application/ogg",
|
|
||||||
"pbm"=>"image/x-portable-bitmap",
|
|
||||||
"dwf"=>"x-drawing/dwf",
|
|
||||||
"smp3"=>"audio/vnd.sealedmedia.softseal.mpeg",
|
|
||||||
"html"=>"text/html",
|
|
||||||
"dwg"=>"image/vnd.dwg",
|
|
||||||
"see"=>"application/vnd.seemail",
|
|
||||||
"igs"=>"model/iges",
|
|
||||||
"siv"=>"application/sieve",
|
|
||||||
"jad"=>"text/vnd.sun.j2me.app-descriptor",
|
|
||||||
"wml"=>"text/vnd.wap.wml",
|
|
||||||
"ustar"=>"application/x-ustar",
|
|
||||||
"vis"=>"application/vnd.visionary",
|
|
||||||
"pkipath"=>"application/pkix-pkipath",
|
|
||||||
"ecelp4800"=>"audio/vnd.nuera.ecelp4800",
|
|
||||||
"ice"=>"x-conference/x-cooltalk",
|
|
||||||
"qcp"=>"audio/QCELP",
|
|
||||||
"ai"=>"application/postscript",
|
|
||||||
"sppt"=>"application/vnd.sealed.ppt",
|
|
||||||
"ltx"=>"application/x-latex",
|
|
||||||
"nim"=>"video/vnd.nokia.interleaved-multimedia",
|
|
||||||
"igx"=>"application/vnd.micrografx.igx",
|
|
||||||
"viv"=>"video/vnd.vivo",
|
|
||||||
"wpl"=>"application/vnd.ms-wpl",
|
|
||||||
"ami"=>"application/vnd.amiga.ami",
|
|
||||||
"tcl"=>"application/x-tcl",
|
|
||||||
"l16"=>"audio/L16",
|
|
||||||
"css"=>"text/css",
|
|
||||||
"vbk"=>"audio/vnd.nortel.vbk",
|
|
||||||
"pki"=>"application/pkixcmp",
|
|
||||||
"ras"=>"image/x-cmu-raster",
|
|
||||||
"jpeg"=>"image/jpeg",
|
|
||||||
"chrt"=>"application/vnd.kde.kchart",
|
|
||||||
"cil"=>"application/vnd.ms-artgalry",
|
|
||||||
"mxu"=>"video/vnd.mpegurl",
|
|
||||||
"xwd"=>"image/x-xwindowdump",
|
|
||||||
"kon"=>"application/vnd.kde.kontour",
|
|
||||||
"dgn"=>"image/x-vnd.dgn",
|
|
||||||
"csv"=>"text/csv",
|
|
||||||
"png"=>"image/png",
|
|
||||||
"xfdf"=>"application/vnd.adobe.xfdf",
|
|
||||||
"asf"=>"application/vnd.ms-asf",
|
|
||||||
"sxls"=>"application/vnd.sealed.xls",
|
|
||||||
"dl"=>"video/dl",
|
|
||||||
"karbon"=>"application/vnd.kde.karbon",
|
|
||||||
"ico"=>"image/vnd.microsoft.icon",
|
|
||||||
"sus"=>"application/vnd.sus-calendar",
|
|
||||||
"pdb"=>"x-chemical/x-pdb",
|
|
||||||
"wif"=>"application/watcherinfo+xml",
|
|
||||||
"ser"=>"application/x-java-serialized-object",
|
|
||||||
"mdi"=>"image/vnd.ms-modi",
|
|
||||||
"qt"=>"video/quicktime",
|
|
||||||
"rtx"=>"text/richtext",
|
|
||||||
"jar"=>"application/x-java-archive",
|
|
||||||
"rcprofile"=>"application/vnd.ipunplugged.rcprofile",
|
|
||||||
"tsv"=>"text/tab-separated-values",
|
|
||||||
"pnm"=>"image/x-portable-anymap",
|
|
||||||
"me"=>"application/x-troff-me",
|
|
||||||
"amr"=>"audio/AMR",
|
|
||||||
"wp5"=>"application/wordperfect5.1",
|
|
||||||
"gl"=>"video/gl",
|
|
||||||
"man"=>"application/x-troff-man",
|
|
||||||
"pdf"=>"application/pdf",
|
|
||||||
"pgb"=>"image/vnd.globalgraphics.pgb",
|
|
||||||
"au"=>"audio/basic",
|
|
||||||
"avi"=>"video/x-msvideo",
|
|
||||||
"wmlsc"=>"application/vnd.wap.wmlscriptc",
|
|
||||||
"wbxml"=>"application/vnd.wap.wbxml",
|
|
||||||
"saf"=>"application/vnd.yamaha.smaf-audio",
|
|
||||||
"gtar"=>"application/x-gtar",
|
|
||||||
"crl"=>"application/pkix-crl",
|
|
||||||
"pti"=>"application/vnd.pvi.ptid1",
|
|
||||||
"rdz"=>"application/vnd.data-vision.rdz",
|
|
||||||
"flo"=>"application/vnd.micrografx.flo",
|
|
||||||
"aif"=>"audio/x-aiff",
|
|
||||||
"qxd"=>"application/vnd.Quark.QuarkXPress",
|
|
||||||
"kne"=>"application/vnd.Kinar",
|
|
||||||
"rpm"=>"audio/x-pn-realaudio-plugin",
|
|
||||||
"lvp"=>"audio/vnd.lucent.voice",
|
|
||||||
"stml"=>"application/vnd.sealedmedia.softseal.html",
|
|
||||||
"sc"=>"application/vnd.ibm.secure-container",
|
|
||||||
"jnlp"=>"application/x-java-jnlp-file",
|
|
||||||
"smov"=>"video/vnd.sealedmedia.softseal.mov",
|
|
||||||
"dvi"=>"application/x-dvi",
|
|
||||||
"jisp"=>"application/vnd.jisp",
|
|
||||||
"wv"=>"application/vnd.wv.csp+wbxml",
|
|
||||||
"mseq"=>"application/vnd.mseq",
|
|
||||||
"mmf"=>"application/vnd.smaf",
|
|
||||||
"mpc"=>"application/vnd.mophun.certificate",
|
|
||||||
"stk"=>"application/hyperstudio",
|
|
||||||
"txd"=>"application/vnd.genomatix.tuxedo",
|
|
||||||
"ent"=>"application/vnd.nervana",
|
|
||||||
"hdf"=>"application/x-hdf",
|
|
||||||
"xml"=>"application/xml",
|
|
||||||
"mpga"=>"audio/mpeg",
|
|
||||||
"sh"=>"application/x-sh",
|
|
||||||
"pgm"=>"image/x-portable-graymap",
|
|
||||||
"lbd"=>"application/vnd.llamagraphics.life-balance.desktop",
|
|
||||||
"flw"=>"application/vnd.kde.kivio",
|
|
||||||
"si"=>"text/vnd.wap.si",
|
|
||||||
"zip"=>"application/zip",
|
|
||||||
"ecelp7470"=>"audio/vnd.nuera.ecelp7470",
|
|
||||||
"lbe"=>"application/vnd.llamagraphics.life-balance.exchange+xml",
|
|
||||||
"p10"=>"application/pkcs10",
|
|
||||||
"ief"=>"image/ief",
|
|
||||||
"doc"=>"application/msword",
|
|
||||||
"efif"=>"application/vnd.picsel",
|
|
||||||
"jpm"=>"image/jpm",
|
|
||||||
"gz"=>"application/x-gzip",
|
|
||||||
"xhtml"=>"application/xhtml+xml",
|
|
||||||
"irm"=>"application/vnd.ibm.rights-management",
|
|
||||||
"bcpio"=>"application/x-bcpio",
|
|
||||||
"mcd"=>"application/vnd.mcd",
|
|
||||||
"ecelp9600"=>"audio/vnd.nuera.ecelp9600",
|
|
||||||
"ms"=>"application/x-troff-ms",
|
|
||||||
"gif"=>"image/gif",
|
|
||||||
"kwd"=>"application/vnd.kde.kword",
|
|
||||||
"wrl"=>"model/vrml",
|
|
||||||
"sl"=>"text/vnd.wap.sl",
|
|
||||||
"xpm"=>"image/x-xpixmap",
|
|
||||||
"cer"=>"application/pkix-cert",
|
|
||||||
"mxmf"=>"audio/vnd.nokia.mobile-xmf",
|
|
||||||
"psb"=>"application/vnd.3gpp.pic-bw-small",
|
|
||||||
"cab"=>"application/vnd.ms-cab-compressed",
|
|
||||||
"rst"=>"text/prs.fallenstein.rst",
|
|
||||||
"p7m"=>"application/pkcs7-mime",
|
|
||||||
"spng"=>"image/vnd.sealed.png",
|
|
||||||
"mj2"=>"video/MJ2",
|
|
||||||
"wbmp"=>"image/vnd.wap.wbmp",
|
|
||||||
"irp"=>"application/vnd.irepository.package+xml",
|
|
||||||
"smht"=>"application/vnd.sealed.mht",
|
|
||||||
"msh"=>"model/mesh",
|
|
||||||
"htke"=>"application/vnd.kenameaapp",
|
|
||||||
"s11"=>"video/vnd.sealed.mpeg1",
|
|
||||||
"mpm"=>"application/vnd.blueice.multipass",
|
|
||||||
"mpn"=>"application/vnd.mophun.application",
|
|
||||||
"dfac"=>"application/vnd.dreamfactory",
|
|
||||||
"pvb"=>"application/vnd.3gpp.pic-bw-var",
|
|
||||||
"lrm"=>"application/vnd.ms-lrm",
|
|
||||||
"tiff"=>"image/tiff",
|
|
||||||
"jp2"=>"image/jp2",
|
|
||||||
"rpss"=>"application/vnd.nokia.radio-presets",
|
|
||||||
"wmlc"=>"application/vnd.wap.wmlc",
|
|
||||||
"rpst"=>"application/vnd.nokia.radio-preset",
|
|
||||||
"etx"=>"text/x-setext",
|
|
||||||
"bmp"=>"image/bmp",
|
|
||||||
"mpp"=>"application/vnd.ms-project",
|
|
||||||
"spf"=>"application/vnd.yamaha.smaf-phrase",
|
|
||||||
"3gp"=>"video/3gpp",
|
|
||||||
"mid"=>"audio/x-midi",
|
|
||||||
"hqx"=>"application/mac-binhex40",
|
|
||||||
"p7s"=>"application/pkcs7-signature",
|
|
||||||
"wbs"=>"application/vnd.criticaltools.wbs+xml",
|
|
||||||
"emm"=>"application/vnd.ibm.electronic-media",
|
|
||||||
"ppm"=>"image/x-portable-pixmap",
|
|
||||||
"texinfo"=>"application/x-texinfo",
|
|
||||||
"mp2"=>"video/mpeg",
|
|
||||||
"jpx"=>"image/jpx",
|
|
||||||
"evc"=>"audio/EVRC",
|
|
||||||
"mif"=>"application/x-mif",
|
|
||||||
"ra"=>"audio/x-realaudio",
|
|
||||||
"spdf"=>"application/vnd.sealedmedia.softseal.pdf",
|
|
||||||
"x_b"=>"model/vnd.parasolid.transmit.binary",
|
|
||||||
"class"=>"application/x-java-vm",
|
|
||||||
"txt"=>"text/plain",
|
|
||||||
"mp4"=>"video/vnd.objectvideo",
|
|
||||||
"hbci"=>"application/vnd.hbci",
|
|
||||||
"wqd"=>"application/vnd.wqd",
|
|
||||||
"vsc"=>"application/vnd.vidsoft.vidconference",
|
|
||||||
"mfm"=>"application/vnd.mfmp",
|
|
||||||
"sgml"=>"text/sgml",
|
|
||||||
"tex"=>"application/x-tex",
|
|
||||||
"curl"=>"application/vnd.curl",
|
|
||||||
"djvu"=>"image/vnd.djvu",
|
|
||||||
"cw"=>"application/prs.cww",
|
|
||||||
"vsd"=>"application/vnd.visio",
|
|
||||||
"tga"=>"image/targa",
|
|
||||||
"wtb"=>"application/vnd.webturbo",
|
|
||||||
"plb"=>"application/vnd.3gpp.pic-bw-large",
|
|
||||||
"t"=>"text/troff",
|
|
||||||
"les"=>"application/vnd.hhe.lesson-player",
|
|
||||||
"sms"=>"application/vnd.3gpp.sms",
|
|
||||||
"hvd"=>"application/vnd.yamaha.hv-dic",
|
|
||||||
"yaml"=>"text/x-yaml",
|
|
||||||
"ppt"=>"application/powerpoint",
|
|
||||||
"psp"=>"image/x-paintshoppro",
|
|
||||||
"sic"=>"application/vnd.wap.sic",
|
|
||||||
"cmc"=>"application/vnd.cosmocaller",
|
|
||||||
"vcf"=>"text/x-vcard",
|
|
||||||
"sjpg"=>"image/vnd.sealedmedia.softseal.jpg",
|
|
||||||
"sid"=>"audio/prs.sid",
|
|
||||||
"sv4cpio"=>"application/x-sv4cpio",
|
|
||||||
"sswf"=>"video/vnd.sealed.swf",
|
|
||||||
"cpio"=>"application/x-cpio",
|
|
||||||
"smv"=>"audio/SMV",
|
|
||||||
"wks"=>"application/vnd.lotus-1-2-3",
|
|
||||||
"sig"=>"application/pgp-signature",
|
|
||||||
"slc"=>"application/vnd.wap.slc",
|
|
||||||
"z"=>"application/x-compressed",
|
|
||||||
"rm"=>"audio/x-pn-realaudio",
|
|
||||||
"bin"=>"application/octet-stream",
|
|
||||||
"smpg"=>"video/vnd.sealed.mpeg4",
|
|
||||||
"wmls"=>"text/vnd.wap.wmlscript",
|
|
||||||
"atc"=>"application/vnd.acucorp",
|
|
||||||
"pfr"=>"application/font-tdpfr",
|
|
||||||
"plj"=>"audio/vnd.everad.plj",
|
|
||||||
"rnd"=>"application/prs.nprend",
|
|
||||||
"xls"=>"application/excel",
|
|
||||||
"sdoc"=>"application/vnd.sealed.doc",
|
|
||||||
"tar"=>"application/x-tar",
|
|
||||||
"oda"=>"application/oda",
|
|
||||||
"kia"=>"application/vnd.kidspiration",
|
|
||||||
"prc"=>"application/vnd.palm",
|
|
||||||
"sgif"=>"image/vnd.sealedmedia.softseal.gif",
|
|
||||||
"soc"=>"application/sgml-open-catalog",
|
|
||||||
"xyz"=>"x-chemical/x-xyz",
|
|
||||||
"awb"=>"audio/AMR-WB",
|
|
||||||
"xbm"=>"image/x-xbitmap",
|
|
||||||
"ccc"=>"text/vnd.net2phone.commcenter.command",
|
|
||||||
"xul"=>"application/vnd.mozilla.xul+xml",
|
|
||||||
"cdy"=>"application/vnd.cinderella",
|
|
||||||
"kpr"=>"application/vnd.kde.kpresenter",
|
|
||||||
"shar"=>"application/x-shar",
|
|
||||||
"src"=>"application/x-wais-source",
|
|
||||||
"hvp"=>"application/vnd.yamaha.hv-voice",
|
|
||||||
"nc"=>"application/netcdf",
|
|
||||||
"sv4crc"=>"application/x-sv4crc",
|
|
||||||
"js" => "text/javascript"
|
|
||||||
}
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,39 +0,0 @@
|
||||||
class Sinatra::Route
|
|
||||||
|
|
||||||
URI_CHAR = '[^/?:,&#]'.freeze unless defined?(URI_CHAR)
|
|
||||||
PARAM = /:(#{URI_CHAR}+)/.freeze unless defined?(PARAM)
|
|
||||||
|
|
||||||
attr_reader :block, :path
|
|
||||||
|
|
||||||
def initialize(path, groups = :all, &b)
|
|
||||||
@path, @groups, @block = path, Array(groups), b
|
|
||||||
@param_keys = []
|
|
||||||
@struct = Struct.new(:path, :groups, :block, :params, :default_status)
|
|
||||||
regex = path.to_s.gsub(PARAM) do
|
|
||||||
@param_keys << $1.intern
|
|
||||||
"(#{URI_CHAR}+)"
|
|
||||||
end
|
|
||||||
if path =~ /:format$/
|
|
||||||
@pattern = /^#{regex}$/
|
|
||||||
else
|
|
||||||
@param_keys << :format
|
|
||||||
@pattern = /^#{regex}(?:\.(#{URI_CHAR}+))?$/
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
def match(path)
|
|
||||||
return nil unless path =~ @pattern
|
|
||||||
params = @param_keys.zip($~.captures.compact.map(&:from_param)).to_hash
|
|
||||||
@struct.new(@path, @groups, @block, include_format(params), 200)
|
|
||||||
end
|
|
||||||
|
|
||||||
def include_format(h)
|
|
||||||
h.delete(:format) unless h[:format]
|
|
||||||
Sinatra.config[:default_params].merge(h)
|
|
||||||
end
|
|
||||||
|
|
||||||
def pretty_print(pp)
|
|
||||||
pp.text "{Route: #{@pattern} : [#{@param_keys.map(&:inspect).join(",")}] : #{@groups.join(",")} }"
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,24 +0,0 @@
|
||||||
require 'test/unit'
|
|
||||||
|
|
||||||
def silence_warnings
|
|
||||||
old_verbose, $VERBOSE = $VERBOSE, nil
|
|
||||||
yield
|
|
||||||
ensure
|
|
||||||
$VERBOSE = old_verbose
|
|
||||||
end
|
|
||||||
|
|
||||||
silence_warnings do
|
|
||||||
require File.dirname(__FILE__) + '/../sinatra'
|
|
||||||
end
|
|
||||||
|
|
||||||
require File.dirname(__FILE__) + "/test/methods"
|
|
||||||
|
|
||||||
Test::Unit::TestCase.send :include, Sinatra::Test::Methods
|
|
||||||
|
|
||||||
Sinatra.default_config[:raise_errors] = true
|
|
||||||
Sinatra.default_config[:env] = :test
|
|
||||||
Sinatra.default_config[:run] = false
|
|
||||||
|
|
||||||
Sinatra.config = nil
|
|
||||||
|
|
||||||
Sinatra.setup_logger
|
|
|
@ -1,45 +0,0 @@
|
||||||
module Sinatra
|
|
||||||
|
|
||||||
module Test
|
|
||||||
|
|
||||||
module Methods
|
|
||||||
|
|
||||||
def get_it(path, params = {})
|
|
||||||
@request = Rack::MockRequest.new(Sinatra)
|
|
||||||
@response = @request.get(path, :input => params.to_params)
|
|
||||||
end
|
|
||||||
|
|
||||||
def post_it(path, params = {})
|
|
||||||
@request = Rack::MockRequest.new(Sinatra)
|
|
||||||
@response = @request.post(path, :input => params.to_params)
|
|
||||||
end
|
|
||||||
|
|
||||||
def put_it(path, params = {})
|
|
||||||
@request = Rack::MockRequest.new(Sinatra)
|
|
||||||
@response = @request.put(path, :input => params.to_params)
|
|
||||||
end
|
|
||||||
|
|
||||||
def delete_it(path, params = {})
|
|
||||||
@request = Rack::MockRequest.new(Sinatra)
|
|
||||||
@response = @request.delete(path, :input => params.to_params)
|
|
||||||
end
|
|
||||||
|
|
||||||
def follow!
|
|
||||||
get_it(@response.location)
|
|
||||||
end
|
|
||||||
|
|
||||||
def dont_raise_errors
|
|
||||||
Sinatra.config[:raise_errors] = false
|
|
||||||
yield
|
|
||||||
Sinatra.config[:raise_errors] = true
|
|
||||||
end
|
|
||||||
|
|
||||||
def method_missing(name, *args)
|
|
||||||
@response.send(name, *args)
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,10 +0,0 @@
|
||||||
require File.dirname(__FILE__) + '/../test'
|
|
||||||
require "test/spec"
|
|
||||||
|
|
||||||
module Sinatra::Test::Methods
|
|
||||||
|
|
||||||
def should
|
|
||||||
@response.should
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,146 +0,0 @@
|
||||||
require File.dirname(__FILE__) + '/helper'
|
|
||||||
|
|
||||||
context "Dispatching" do
|
|
||||||
|
|
||||||
setup do
|
|
||||||
Sinatra.reset!
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
specify "should return the correct block" do
|
|
||||||
r = get '/' do
|
|
||||||
'main'
|
|
||||||
end
|
|
||||||
|
|
||||||
result = Sinatra.determine_route(:get, '/')
|
|
||||||
result.path.should.equal r.first.path
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should return custom 404" do
|
|
||||||
Sinatra.routes[404] = r = Proc.new { 'custom 404' }
|
|
||||||
|
|
||||||
result = Sinatra.determine_route(:get, '/')
|
|
||||||
result.should.be r
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should return standard 404" do
|
|
||||||
get_it '/'
|
|
||||||
status.should.equal 404
|
|
||||||
body.should.equal '<h1>Not Found</h1>'
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should give custom 500 if error when called" do
|
|
||||||
Sinatra.routes[500] = r = Proc.new { 'custom 500' }
|
|
||||||
|
|
||||||
get '/' do
|
|
||||||
raise 'asdf'
|
|
||||||
end
|
|
||||||
|
|
||||||
dont_raise_errors do
|
|
||||||
get_it '/'
|
|
||||||
end
|
|
||||||
|
|
||||||
body.should.equal 'custom 500'
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should give standard 500 if error when called" do
|
|
||||||
get '/' do
|
|
||||||
raise 'asdf'
|
|
||||||
end
|
|
||||||
|
|
||||||
dont_raise_errors do
|
|
||||||
get_it '/'
|
|
||||||
end
|
|
||||||
|
|
||||||
body.should.match(/^<h2>asdf<\/h2>/)
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should run in a context" do
|
|
||||||
Sinatra::EventContext.any_instance.expects(:foo).returns 'in foo'
|
|
||||||
|
|
||||||
get '/' do
|
|
||||||
foo
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/'
|
|
||||||
body.should.equal 'in foo'
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "has access to the request" do
|
|
||||||
|
|
||||||
get '/blake' do
|
|
||||||
request.path_info
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/blake'
|
|
||||||
|
|
||||||
body.should.equal '/blake'
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "has DSLified methods for response" do
|
|
||||||
get '/' do
|
|
||||||
status 555
|
|
||||||
'uh oh'
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/'
|
|
||||||
|
|
||||||
body.should.equal "uh oh"
|
|
||||||
status.should.equal 555
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should give format for free" do
|
|
||||||
get '/formatted' do
|
|
||||||
params[:format].should.equal 'xml'
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/formatted.xml'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should give format default html format for free" do
|
|
||||||
get '/formatted' do
|
|
||||||
params[:format].should.equal 'html'
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/formatted'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "format for free is overrided by :format in route" do
|
|
||||||
|
|
||||||
get '/formatted.:format' do
|
|
||||||
params[:format]
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/formatted.xml'
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'xml'
|
|
||||||
|
|
||||||
get_it '/formatted.js'
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'js'
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
context "An Event in test mode" do
|
|
||||||
|
|
||||||
setup do
|
|
||||||
Sinatra.routes.clear
|
|
||||||
Sinatra.setup_default_events!
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should raise errors to top" do
|
|
||||||
get '/' do
|
|
||||||
raise 'asdf'
|
|
||||||
end
|
|
||||||
|
|
||||||
lambda { get_it '/' }.should.raise(RuntimeError)
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,50 +0,0 @@
|
||||||
require File.dirname(__FILE__) + '/helper'
|
|
||||||
|
|
||||||
context "Defining Errors" do
|
|
||||||
|
|
||||||
setup do
|
|
||||||
Sinatra.reset!
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should raise error if no block given" do
|
|
||||||
|
|
||||||
lambda { error 404 }.should.raise(RuntimeError)
|
|
||||||
lambda { error(404) {} }.should.not.raise
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should auto-set status for error events" do
|
|
||||||
error 404 do
|
|
||||||
'custom 404'
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/'
|
|
||||||
|
|
||||||
should.be.not_found
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should handle multiple errors" do
|
|
||||||
|
|
||||||
error 404, 500 do
|
|
||||||
'multi custom error'
|
|
||||||
end
|
|
||||||
|
|
||||||
get '/error' do
|
|
||||||
raise 'asdf'
|
|
||||||
end
|
|
||||||
|
|
||||||
dont_raise_errors do
|
|
||||||
get_it '/error'
|
|
||||||
end
|
|
||||||
|
|
||||||
status.should.equal 500
|
|
||||||
body.should.equal 'multi custom error'
|
|
||||||
|
|
||||||
get_it '/'
|
|
||||||
status.should.equal 404
|
|
||||||
|
|
||||||
body.should.equal 'multi custom error'
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,39 +0,0 @@
|
||||||
require File.dirname(__FILE__) + '/helper'
|
|
||||||
|
|
||||||
context "Event's DSL" do
|
|
||||||
|
|
||||||
setup do
|
|
||||||
Sinatra.reset!
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "takes multiple routes" do
|
|
||||||
|
|
||||||
get '/', '/foo' do
|
|
||||||
'hello from me'
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/'
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'hello from me'
|
|
||||||
|
|
||||||
get_it '/foo'
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'hello from me'
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should be able to halt from within request" do
|
|
||||||
|
|
||||||
get '/halting' do
|
|
||||||
throw :halt, 'halted'
|
|
||||||
'not this'
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/halting'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'halted'
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,113 +0,0 @@
|
||||||
require File.dirname(__FILE__) + '/helper'
|
|
||||||
|
|
||||||
class CustomResult
|
|
||||||
|
|
||||||
def to_result(cx, *args)
|
|
||||||
cx.status 404
|
|
||||||
cx.body "Can't find this shit!"
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
context "Filters" do
|
|
||||||
|
|
||||||
setup do
|
|
||||||
Sinatra.reset!
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "halts when told" do
|
|
||||||
|
|
||||||
before do
|
|
||||||
throw :halt, 'fubar'
|
|
||||||
end
|
|
||||||
|
|
||||||
get '/' do
|
|
||||||
'not this'
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'fubar'
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "halts with status" do
|
|
||||||
|
|
||||||
before do
|
|
||||||
throw :halt, [401, 'get out dude!']
|
|
||||||
end
|
|
||||||
|
|
||||||
get '/auth' do
|
|
||||||
"you're in!"
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/auth'
|
|
||||||
|
|
||||||
status.should.equal 401
|
|
||||||
body.should.equal 'get out dude!'
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "halts with custom result" do
|
|
||||||
|
|
||||||
before do
|
|
||||||
throw :halt, CustomResult.new
|
|
||||||
end
|
|
||||||
|
|
||||||
get '/custom' do
|
|
||||||
'not this'
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/custom'
|
|
||||||
|
|
||||||
should.be.not_found
|
|
||||||
body.should.equal "Can't find this shit!"
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
context "Filter grouping" do
|
|
||||||
|
|
||||||
setup do
|
|
||||||
Sinatra.reset!
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "befores only run for groups if specified" do
|
|
||||||
|
|
||||||
Sinatra::EventContext.any_instance.expects(:foo).times(4)
|
|
||||||
|
|
||||||
before do
|
|
||||||
foo # this should be called before all events
|
|
||||||
end
|
|
||||||
|
|
||||||
after do
|
|
||||||
foo
|
|
||||||
end
|
|
||||||
|
|
||||||
before :admins do
|
|
||||||
throw :halt, 'not authorized'
|
|
||||||
end
|
|
||||||
|
|
||||||
get '/', :groups => :admins do
|
|
||||||
'asdf'
|
|
||||||
end
|
|
||||||
|
|
||||||
get '/foo' do
|
|
||||||
'yeah!'
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'not authorized'
|
|
||||||
|
|
||||||
get_it '/foo'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'yeah!'
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,3 +0,0 @@
|
||||||
require File.dirname(__FILE__) + '/../lib/sinatra/test/spec'
|
|
||||||
require 'mocha'
|
|
||||||
|
|
|
@ -1,28 +0,0 @@
|
||||||
require File.dirname(__FILE__) + '/helper'
|
|
||||||
|
|
||||||
context "Helpers" do
|
|
||||||
|
|
||||||
setup do
|
|
||||||
Sinatra.reset!
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "for event context" do
|
|
||||||
|
|
||||||
helpers do
|
|
||||||
def foo
|
|
||||||
'foo'
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
get '/' do
|
|
||||||
foo
|
|
||||||
end
|
|
||||||
|
|
||||||
get_it '/'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'foo'
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1 +0,0 @@
|
||||||
bar
|
|
|
@ -1 +0,0 @@
|
||||||
<foo></foo>
|
|
|
@ -1 +0,0 @@
|
||||||
var i = 11;
|
|
|
@ -1 +0,0 @@
|
||||||
abc
|
|
|
@ -1,40 +0,0 @@
|
||||||
require File.dirname(__FILE__) + '/helper'
|
|
||||||
|
|
||||||
context "A Route in general" do
|
|
||||||
|
|
||||||
specify "matches a path to a block" do
|
|
||||||
e = Sinatra::Route.new('/') do
|
|
||||||
'hello'
|
|
||||||
end
|
|
||||||
|
|
||||||
result = e.match('/')
|
|
||||||
result.block.call.should.equal 'hello'
|
|
||||||
result.params.should.equal :format => 'html'
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "matches with params from path" do
|
|
||||||
e = Sinatra::Route.new('/:name') do
|
|
||||||
'hello again'
|
|
||||||
end
|
|
||||||
|
|
||||||
# spaces should work
|
|
||||||
result = e.match('/blake%20mizerany')
|
|
||||||
result.should.not.be.nil
|
|
||||||
result.block.call.should.equal 'hello again'
|
|
||||||
result.params.should.equal :name => 'blake mizerany', :format => "html"
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "matches multiple vars in path" do
|
|
||||||
e = Sinatra::Route.new('/:name/:age') do
|
|
||||||
'hello again'
|
|
||||||
end
|
|
||||||
|
|
||||||
# spaces should work
|
|
||||||
result = e.match('/blake%20mizerany/25')
|
|
||||||
result.should.not.be.nil
|
|
||||||
result.block.call.should.equal 'hello again'
|
|
||||||
result.params.should.equal :name => 'blake mizerany', :age => '25',
|
|
||||||
:format => "html"
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,62 +0,0 @@
|
||||||
require File.dirname(__FILE__) + '/helper'
|
|
||||||
|
|
||||||
context "Static" do
|
|
||||||
|
|
||||||
setup do
|
|
||||||
Sinatra.reset!
|
|
||||||
Sinatra.config[:root] = File.dirname(__FILE__)
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "sends files" do
|
|
||||||
|
|
||||||
get_it '/foo.xml'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal '<foo></foo>'
|
|
||||||
headers.should.equal 'Content-Type' => 'application/xml',
|
|
||||||
'Content-Length' => '<foo></foo>'.size
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "defaults to text/plain" do
|
|
||||||
|
|
||||||
get_it '/foo.foo'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'bar'
|
|
||||||
headers.should.equal 'Content-Type' => 'text/plain',
|
|
||||||
'Content-Length' => 'bar'.size
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "default to user definied type" do
|
|
||||||
Sinatra.config[:default_static_mime_type] = 'foo/bar'
|
|
||||||
|
|
||||||
get_it '/foo.foo'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'bar'
|
|
||||||
headers.should.equal 'Content-Type' => 'foo/bar',
|
|
||||||
'Content-Length' => 'bar'.size
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "handles files without ext" do
|
|
||||||
get_it '/xyz'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'abc'
|
|
||||||
headers.should.equal 'Content-Type' => 'text/plain',
|
|
||||||
'Content-Length' => 'bar'.size
|
|
||||||
end
|
|
||||||
|
|
||||||
specify "should handle javascript correctly" do
|
|
||||||
|
|
||||||
get_it '/test.js'
|
|
||||||
|
|
||||||
should.be.ok
|
|
||||||
body.should.equal 'var i = 11;'
|
|
||||||
headers.should.equal 'Content-Type' => 'text/javascript',
|
|
||||||
'Content-Length' => 'var i = 11;'.size
|
|
||||||
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
|
@ -1,12 +0,0 @@
|
||||||
require File.dirname(__FILE__) + '/../lib/sinatra'
|
|
||||||
require File.dirname(__FILE__) + '/../lib/sinatra/test'
|
|
||||||
|
|
||||||
class TestTest < Test::Unit::TestCase
|
|
||||||
|
|
||||||
def test_test
|
|
||||||
get_it '/'
|
|
||||||
assert_equal 404, status
|
|
||||||
assert_equal '<h1>Not Found</h1>', body
|
|
||||||
end
|
|
||||||
|
|
||||||
end
|
|
Loading…
Reference in a new issue