sinatra 2.0.8.1 → 2.2.0

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of sinatra might be problematic. Click here for more details.

data/lib/sinatra/base.rb CHANGED
@@ -43,12 +43,11 @@ module Sinatra
43
43
  end
44
44
 
45
45
  def preferred_type(*types)
46
- accepts = accept # just evaluate once
47
- return accepts.first if types.empty?
46
+ return accept.first if types.empty?
48
47
  types.flatten!
49
- return types.first if accepts.empty?
50
- accepts.detect do |pattern|
51
- type = types.detect { |t| File.fnmatch(pattern, t) }
48
+ return types.first if accept.empty?
49
+ accept.detect do |accept_header|
50
+ type = types.detect { |t| MimeTypeEntry.new(t).accepts?(accept_header) }
52
51
  return type if type
53
52
  end
54
53
  end
@@ -79,10 +78,10 @@ module Sinatra
79
78
  super
80
79
  rescue Rack::Utils::ParameterTypeError, Rack::Utils::InvalidParameterError => e
81
80
  raise BadRequest, "Invalid query parameters: #{Rack::Utils.escape_html(e.message)}"
81
+ rescue EOFError => e
82
+ raise BadRequest, "Invalid multipart/form-data: #{Rack::Utils.escape_html(e.message)}"
82
83
  end
83
84
 
84
- private
85
-
86
85
  class AcceptEntry
87
86
  attr_accessor :params
88
87
  attr_reader :entry
@@ -125,6 +124,35 @@ module Sinatra
125
124
  to_str.send(*args, &block)
126
125
  end
127
126
  end
127
+
128
+ class MimeTypeEntry
129
+ attr_reader :params
130
+
131
+ def initialize(entry)
132
+ params = entry.scan(HEADER_PARAM).map! do |s|
133
+ key, value = s.strip.split('=', 2)
134
+ value = value[1..-2].gsub(/\\(.)/, '\1') if value.start_with?('"')
135
+ [key, value]
136
+ end
137
+
138
+ @type = entry[/[^;]+/].delete(' ')
139
+ @params = Hash[params]
140
+ end
141
+
142
+ def accepts?(entry)
143
+ File.fnmatch(entry, self) && matches_params?(entry.params)
144
+ end
145
+
146
+ def to_str
147
+ @type
148
+ end
149
+
150
+ def matches_params?(params)
151
+ return true if @params.empty?
152
+
153
+ params.all? { |k,v| !@params.has_key?(k) || @params[k] == v }
154
+ end
155
+ end
128
156
  end
129
157
 
130
158
  # The response object. See Rack::Response and Rack::Response::Helpers for
@@ -133,10 +161,6 @@ module Sinatra
133
161
  # http://rubydoc.info/github/rack/rack/master/Rack/Response/Helpers
134
162
  class Response < Rack::Response
135
163
  DROP_BODY_RESPONSES = [204, 304]
136
- def initialize(*)
137
- super
138
- headers['Content-Type'] ||= 'text/html'
139
- end
140
164
 
141
165
  def body=(value)
142
166
  value = value.body while Rack::Response === value
@@ -163,10 +187,10 @@ module Sinatra
163
187
  if calculate_content_length?
164
188
  # if some other code has already set Content-Length, don't muck with it
165
189
  # currently, this would be the static file-handler
166
- headers["Content-Length"] = body.inject(0) { |l, p| l + p.bytesize }.to_s
190
+ headers["Content-Length"] = body.map(&:bytesize).reduce(0, :+).to_s
167
191
  end
168
192
 
169
- [status.to_i, headers, result]
193
+ [status, headers, result]
170
194
  end
171
195
 
172
196
  private
@@ -176,15 +200,15 @@ module Sinatra
176
200
  end
177
201
 
178
202
  def drop_content_info?
179
- status.to_i / 100 == 1 or drop_body?
203
+ informational? or drop_body?
180
204
  end
181
205
 
182
206
  def drop_body?
183
- DROP_BODY_RESPONSES.include?(status.to_i)
207
+ DROP_BODY_RESPONSES.include?(status)
184
208
  end
185
209
  end
186
210
 
187
- # Some Rack handlers (Thin, Rainbows!) implement an extended body object protocol, however,
211
+ # Some Rack handlers (Rainbows!) implement an extended body object protocol, however,
188
212
  # some middleware (namely Rack::Lint) will break it by not mirroring the methods in question.
189
213
  # This middleware will detect an extended body object and will make sure it reaches the
190
214
  # handler directly. We do this here, so our middleware and middleware set up by the app will
@@ -451,7 +475,7 @@ module Sinatra
451
475
  #
452
476
  # The close parameter specifies whether Stream#close should be called
453
477
  # after the block has been executed. This is only relevant for evented
454
- # servers like Thin or Rainbows.
478
+ # servers like Rainbows.
455
479
  def stream(keep_open = false)
456
480
  scheduler = env['async.callback'] ? EventMachine : Stream
457
481
  current = @params.dup
@@ -647,8 +671,6 @@ module Sinatra
647
671
  end
648
672
  end
649
673
 
650
- private
651
-
652
674
  # Template rendering methods. Each method takes the name of a template
653
675
  # to render as a Symbol and returns a String with the rendered output,
654
676
  # as well as an optional hash with additional options.
@@ -849,12 +871,12 @@ module Sinatra
849
871
 
850
872
  def compile_template(engine, data, options, views)
851
873
  eat_errors = options.delete :eat_errors
852
- template_cache.fetch engine, data, options, views do
853
- template = Tilt[engine]
854
- raise "Template engine not found: #{engine}" if template.nil?
874
+ template = Tilt[engine]
875
+ raise "Template engine not found: #{engine}" if template.nil?
855
876
 
856
- case data
857
- when Symbol
877
+ case data
878
+ when Symbol
879
+ template_cache.fetch engine, data, options, views do
858
880
  body, path, line = settings.templates[data]
859
881
  if body
860
882
  body = body.call if body.respond_to?(:call)
@@ -872,17 +894,24 @@ module Sinatra
872
894
  throw :layout_missing if eat_errors and not found
873
895
  template.new(path, 1, options)
874
896
  end
875
- when Proc, String
876
- body = data.is_a?(String) ? Proc.new { data } : data
877
- caller = settings.caller_locations.first
878
- path = options[:path] || caller[0]
879
- line = options[:line] || caller[1]
880
- template.new(path, line.to_i, options, &body)
881
- else
882
- raise ArgumentError, "Sorry, don't know how to render #{data.inspect}."
883
897
  end
898
+ when Proc
899
+ compile_block_template(template, options, &data)
900
+ when String
901
+ template_cache.fetch engine, data, options, views do
902
+ compile_block_template(template, options) { data }
903
+ end
904
+ else
905
+ raise ArgumentError, "Sorry, don't know how to render #{data.inspect}."
884
906
  end
885
907
  end
908
+
909
+ def compile_block_template(template, options, &body)
910
+ caller = settings.caller_locations.first
911
+ path = options[:path] || caller[0]
912
+ line = options[:line] || caller[1]
913
+ template.new(path, line.to_i, options, &body)
914
+ end
886
915
  end
887
916
 
888
917
  # Base class for all Sinatra applications and middleware.
@@ -896,10 +925,11 @@ module Sinatra
896
925
  attr_accessor :app, :env, :request, :response, :params
897
926
  attr_reader :template_cache
898
927
 
899
- def initialize(app = nil)
928
+ def initialize(app = nil, **kwargs)
900
929
  super()
901
930
  @app = app
902
931
  @template_cache = Tilt::Cache.new
932
+ @pinned_response = nil # whether a before! filter pinned the content-type
903
933
  yield self if block_given?
904
934
  end
905
935
 
@@ -913,17 +943,17 @@ module Sinatra
913
943
  @params = IndifferentHash.new
914
944
  @request = Request.new(env)
915
945
  @response = Response.new
946
+ @pinned_response = nil
916
947
  template_cache.clear if settings.reload_templates
917
948
 
918
- @response['Content-Type'] = nil
919
949
  invoke { dispatch! }
920
950
  invoke { error_block!(response.status) } unless @env['sinatra.error']
921
951
 
922
952
  unless @response['Content-Type']
923
- if Array === body and body[0].respond_to? :content_type
953
+ if Array === body && body[0].respond_to?(:content_type)
924
954
  content_type body[0].content_type
925
- else
926
- content_type :html
955
+ elsif default = settings.default_content_type
956
+ content_type default
927
957
  end
928
958
  end
929
959
 
@@ -973,15 +1003,21 @@ module Sinatra
973
1003
  private
974
1004
 
975
1005
  # Run filters defined on the class and all superclasses.
976
- def filter!(type, base = settings)
977
- filter! type, base.superclass if base.superclass.respond_to?(:filters)
978
- base.filters[type].each { |args| process_route(*args) }
1006
+ # Accepts an optional block to call after each filter is applied.
1007
+ def filter!(type, base = settings, &block)
1008
+ filter!(type, base.superclass, &block) if base.superclass.respond_to?(:filters)
1009
+ base.filters[type].each do |args|
1010
+ result = process_route(*args)
1011
+ block.call(result) if block_given?
1012
+ end
979
1013
  end
980
1014
 
981
1015
  # Run routes defined on the class and all superclasses.
982
1016
  def route!(base = settings, pass_block = nil)
983
1017
  if routes = base.routes[@request.request_method]
984
1018
  routes.each do |pattern, conditions, block|
1019
+ response.delete_header('Content-Type') unless @pinned_response
1020
+
985
1021
  returned_pass_block = process_route(pattern, conditions) do |*args|
986
1022
  env['sinatra.route'] = "#{@request.request_method} #{pattern}"
987
1023
  route_eval { block[*args] }
@@ -1059,7 +1095,11 @@ module Sinatra
1059
1095
  # a matching file is found, returns nil otherwise.
1060
1096
  def static!(options = {})
1061
1097
  return if (public_dir = settings.public_folder).nil?
1062
- path = File.expand_path("#{public_dir}#{URI_INSTANCE.unescape(request.path_info)}" )
1098
+ path = "#{public_dir}#{URI_INSTANCE.unescape(request.path_info)}"
1099
+ return unless valid_path?(path)
1100
+
1101
+ path = File.expand_path(path)
1102
+ return unless path.start_with?(File.expand_path(public_dir) + '/')
1063
1103
  return unless File.file?(path)
1064
1104
 
1065
1105
  env['sinatra.static_file'] = path
@@ -1094,7 +1134,9 @@ module Sinatra
1094
1134
 
1095
1135
  invoke do
1096
1136
  static! if settings.static? && (request.get? || request.head?)
1097
- filter! :before
1137
+ filter! :before do
1138
+ @pinned_response = !response['Content-Type'].nil?
1139
+ end
1098
1140
  route!
1099
1141
  end
1100
1142
  rescue ::Exception => boom
@@ -1114,7 +1156,7 @@ module Sinatra
1114
1156
  end
1115
1157
  @env['sinatra.error'] = boom
1116
1158
 
1117
- if boom.respond_to? :http_status
1159
+ if boom.respond_to? :http_status and boom.http_status.between? 400, 599
1118
1160
  status(boom.http_status)
1119
1161
  elsif settings.use_code? and boom.respond_to? :code and boom.code.between? 400, 599
1120
1162
  status(boom.code)
@@ -1122,21 +1164,27 @@ module Sinatra
1122
1164
  status(500)
1123
1165
  end
1124
1166
 
1125
- status(500) unless status.between? 400, 599
1126
-
1127
- boom_message = boom.message if boom.message && boom.message != boom.class.name
1128
1167
  if server_error?
1129
1168
  dump_errors! boom if settings.dump_errors?
1130
1169
  raise boom if settings.show_exceptions? and settings.show_exceptions != :after_handler
1131
1170
  elsif not_found?
1132
1171
  headers['X-Cascade'] = 'pass' if settings.x_cascade?
1133
- body boom_message || '<h1>Not Found</h1>'
1134
- elsif bad_request?
1135
- body boom_message || '<h1>Bad Request</h1>'
1136
1172
  end
1137
1173
 
1138
- res = error_block!(boom.class, boom) || error_block!(status, boom)
1139
- return res if res or not server_error?
1174
+ if res = error_block!(boom.class, boom) || error_block!(status, boom)
1175
+ return res
1176
+ end
1177
+
1178
+ if not_found? || bad_request?
1179
+ if boom.message && boom.message != boom.class.name
1180
+ body Rack::Utils.escape_html(boom.message)
1181
+ else
1182
+ content_type 'text/html'
1183
+ body '<h1>' + (not_found? ? 'Not Found' : 'Bad Request') + '</h1>'
1184
+ end
1185
+ end
1186
+
1187
+ return unless server_error?
1140
1188
  raise boom if settings.raise_errors? or settings.show_exceptions?
1141
1189
  error_block! Exception, boom
1142
1190
  end
@@ -1432,6 +1480,7 @@ module Sinatra
1432
1480
  @prototype = nil
1433
1481
  @middleware << [middleware, args, block]
1434
1482
  end
1483
+ ruby2_keywords(:use) if respond_to?(:ruby2_keywords, true)
1435
1484
 
1436
1485
  # Stop the self-hosted server if running.
1437
1486
  def quit!
@@ -1446,12 +1495,12 @@ module Sinatra
1446
1495
  alias_method :stop!, :quit!
1447
1496
 
1448
1497
  # Run the Sinatra app as a self-hosted server using
1449
- # Thin, Puma, Mongrel, or WEBrick (in that order). If given a block, will call
1498
+ # Puma, Mongrel, or WEBrick (in that order). If given a block, will call
1450
1499
  # with the constructed handler once we have taken the stage.
1451
1500
  def run!(options = {}, &block)
1452
1501
  return if running?
1453
1502
  set options
1454
- handler = detect_rack_handler
1503
+ handler = Rack::Handler.pick(server)
1455
1504
  handler_name = handler.name.gsub(/.*::/, '')
1456
1505
  server_settings = settings.respond_to?(:server_settings) ? settings.server_settings : {}
1457
1506
  server_settings.merge!(:Port => port, :Host => bind)
@@ -1484,8 +1533,8 @@ module Sinatra
1484
1533
  # Create a new instance of the class fronted by its middleware
1485
1534
  # pipeline. The object is guaranteed to respond to #call but may not be
1486
1535
  # an instance of the class new was called on.
1487
- def new(*args, &bk)
1488
- instance = new!(*args, &bk)
1536
+ def new(*args, **kwargs, &bk)
1537
+ instance = new!(*args, **kwargs, &bk)
1489
1538
  Wrapper.new(build(instance).to_app, instance)
1490
1539
  end
1491
1540
 
@@ -1523,7 +1572,7 @@ module Sinatra
1523
1572
  # behavior, by ensuring an instance exists:
1524
1573
  prototype
1525
1574
  # Run the instance we created:
1526
- handler.run(self, server_settings) do |server|
1575
+ handler.run(self, **server_settings) do |server|
1527
1576
  unless suppress_messages?
1528
1577
  $stderr.puts "== Sinatra (v#{Sinatra::VERSION}) has taken the stage on #{port} for #{environment} with backup from #{handler_name}"
1529
1578
  end
@@ -1705,17 +1754,6 @@ module Sinatra
1705
1754
  builder.use session_store, options
1706
1755
  end
1707
1756
 
1708
- def detect_rack_handler
1709
- servers = Array(server)
1710
- servers.each do |server_name|
1711
- begin
1712
- return Rack::Handler.get(server_name.to_s)
1713
- rescue LoadError, NameError
1714
- end
1715
- end
1716
- fail "Server handler (#{servers.join(',')}) not found."
1717
- end
1718
-
1719
1757
  def inherited(subclass)
1720
1758
  subclass.reset!
1721
1759
  subclass.set :app_file, caller_files.first unless subclass.app_file?
@@ -1777,6 +1815,7 @@ module Sinatra
1777
1815
  set :add_charset, %w[javascript xml xhtml+xml].map { |t| "application/#{t}" }
1778
1816
  settings.add_charset << /^text\//
1779
1817
  set :mustermann_opts, {}
1818
+ set :default_content_type, 'text/html'
1780
1819
 
1781
1820
  # explicitly generating a session secret eagerly to play nice with preforking
1782
1821
  begin
@@ -1837,7 +1876,7 @@ module Sinatra
1837
1876
 
1838
1877
  configure :development do
1839
1878
  get '/__sinatra__/:image.png' do
1840
- filename = File.dirname(__FILE__) + "/images/#{params[:image].to_i}.png"
1879
+ filename = __dir__ + "/images/#{params[:image].to_i}.png"
1841
1880
  content_type :png
1842
1881
  send_file filename
1843
1882
  end
@@ -1918,6 +1957,8 @@ module Sinatra
1918
1957
  return super(*args, &block) if respond_to? method_name
1919
1958
  Delegator.target.send(method_name, *args, &block)
1920
1959
  end
1960
+ # ensure keyword argument passing is compatible with ruby >= 2.7
1961
+ ruby2_keywords(method_name) if respond_to?(:ruby2_keywords, true)
1921
1962
  private method_name
1922
1963
  end
1923
1964
  end
@@ -180,6 +180,20 @@ module Sinatra
180
180
  end
181
181
  end
182
182
 
183
+ def select(*args, &block)
184
+ return to_enum(:select) unless block_given?
185
+ dup.tap { |hash| hash.select!(*args, &block) }
186
+ end
187
+
188
+ def reject(*args, &block)
189
+ return to_enum(:reject) unless block_given?
190
+ dup.tap { |hash| hash.reject!(*args, &block) }
191
+ end
192
+
193
+ def compact
194
+ dup.tap(&:compact!)
195
+ end if method_defined?(:compact) # Added in Ruby 2.4
196
+
183
197
  private
184
198
 
185
199
  def convert_key(key)
data/lib/sinatra/main.rb CHANGED
@@ -4,11 +4,11 @@ module Sinatra
4
4
  if ARGV.any?
5
5
  require 'optparse'
6
6
  parser = OptionParser.new { |op|
7
- op.on('-p port', 'set the port (default is 4567)') { |val| ParamsConfig[:port] = Integer(val) }
8
- op.on('-s server', 'specify rack server/handler (default is thin)') { |val| ParamsConfig[:server] = val }
9
- op.on('-q', 'turn on quiet mode (default is off)') { ParamsConfig[:quiet] = true }
10
- op.on('-x', 'turn on the mutex lock (default is off)') { ParamsConfig[:lock] = true }
11
- op.on('-e env', 'set the environment (default is development)') do |val|
7
+ op.on('-p port', 'set the port (default is 4567)') { |val| ParamsConfig[:port] = Integer(val) }
8
+ op.on('-s server', 'specify rack server/handler') { |val| ParamsConfig[:server] = val }
9
+ op.on('-q', 'turn on quiet mode (default is off)') { ParamsConfig[:quiet] = true }
10
+ op.on('-x', 'turn on the mutex lock (default is off)') { ParamsConfig[:lock] = true }
11
+ op.on('-e env', 'set the environment (default is development)') do |val|
12
12
  ENV['RACK_ENV'] = val
13
13
  ParamsConfig[:environment] = val.to_sym
14
14
  end
@@ -43,43 +43,8 @@ module Sinatra
43
43
  ]
44
44
  end
45
45
 
46
- # Pulled from Rack::ShowExceptions in order to override TEMPLATE.
47
- # If Rack provides another way to override, this could be removed
48
- # in the future.
49
- def pretty(env, exception)
50
- req = Rack::Request.new(env)
51
-
52
- # This double assignment is to prevent an "unused variable" warning on
53
- # Ruby 1.9.3. Yes, it is dumb, but I don't like Ruby yelling at me.
54
- path = path = (req.script_name + req.path_info).squeeze("/")
55
-
56
- # This double assignment is to prevent an "unused variable" warning on
57
- # Ruby 1.9.3. Yes, it is dumb, but I don't like Ruby yelling at me.
58
- frames = frames = exception.backtrace.map { |line|
59
- frame = OpenStruct.new
60
- if line =~ /(.*?):(\d+)(:in `(.*)')?/
61
- frame.filename = $1
62
- frame.lineno = $2.to_i
63
- frame.function = $4
64
-
65
- begin
66
- lineno = frame.lineno-1
67
- lines = ::File.readlines(frame.filename)
68
- frame.pre_context_lineno = [lineno-CONTEXT, 0].max
69
- frame.pre_context = lines[frame.pre_context_lineno...lineno]
70
- frame.context_line = lines[lineno].chomp
71
- frame.post_context_lineno = [lineno+CONTEXT, lines.size].min
72
- frame.post_context = lines[lineno+1..frame.post_context_lineno]
73
- rescue
74
- end
75
-
76
- frame
77
- else
78
- nil
79
- end
80
- }.compact
81
-
82
- TEMPLATE.result(binding)
46
+ def template
47
+ TEMPLATE
83
48
  end
84
49
 
85
50
  private
@@ -1,3 +1,3 @@
1
1
  module Sinatra
2
- VERSION = '2.0.8.1'
2
+ VERSION = '2.2.0'
3
3
  end
data/sinatra.gemspec CHANGED
@@ -19,9 +19,8 @@ Gem::Specification.new 'sinatra', version do |s|
19
19
  "SECURITY.md",
20
20
  "sinatra.gemspec",
21
21
  "VERSION"]
22
- s.test_files = s.files.select { |p| p =~ /^test\/.*_test.rb/ }
23
- s.extra_rdoc_files = s.files.select { |p| p =~ /^README/ } << 'LICENSE'
24
- s.rdoc_options = %w[--line-numbers --inline-source --title Sinatra --main README.rdoc --encoding=UTF-8]
22
+ s.extra_rdoc_files = %w[README.md LICENSE]
23
+ s.rdoc_options = %w[--line-numbers --title Sinatra --main README.rdoc --encoding=UTF-8]
25
24
 
26
25
  if s.respond_to?(:metadata)
27
26
  s.metadata = {
@@ -33,11 +32,6 @@ Gem::Specification.new 'sinatra', version do |s|
33
32
  'documentation_uri' => 'https://www.rubydoc.info/gems/sinatra'
34
33
  }
35
34
  else
36
- msg = "RubyGems 2.0 or newer is required to protect against public "\
37
- "gem pushes. You can update your rubygems version by running:\n\n"\
38
- "gem install rubygems-update\n"\
39
- "update_rubygems\n"\
40
- "gem update --system"
41
35
  raise <<-EOF
42
36
  RubyGems 2.0 or newer is required to protect against public gem pushes. You can update your rubygems version by running:
43
37
  gem install rubygems-update
@@ -46,9 +40,9 @@ RubyGems 2.0 or newer is required to protect against public gem pushes. You can
46
40
  EOF
47
41
  end
48
42
 
49
- s.required_ruby_version = '>= 2.2.0'
43
+ s.required_ruby_version = '>= 2.3.0'
50
44
 
51
- s.add_dependency 'rack', '~> 2.0'
45
+ s.add_dependency 'rack', '~> 2.2'
52
46
  s.add_dependency 'tilt', '~> 2.0'
53
47
  s.add_dependency 'rack-protection', version
54
48
  s.add_dependency 'mustermann', '~> 1.0'
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sinatra
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.8.1
4
+ version: 2.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Blake Mizerany
@@ -11,7 +11,7 @@ authors:
11
11
  autorequire:
12
12
  bindir: bin
13
13
  cert_chain: []
14
- date: 2020-01-01 00:00:00.000000000 Z
14
+ date: 2022-02-15 00:00:00.000000000 Z
15
15
  dependencies:
16
16
  - !ruby/object:Gem::Dependency
17
17
  name: rack
@@ -19,14 +19,14 @@ dependencies:
19
19
  requirements:
20
20
  - - "~>"
21
21
  - !ruby/object:Gem::Version
22
- version: '2.0'
22
+ version: '2.2'
23
23
  type: :runtime
24
24
  prerelease: false
25
25
  version_requirements: !ruby/object:Gem::Requirement
26
26
  requirements:
27
27
  - - "~>"
28
28
  - !ruby/object:Gem::Version
29
- version: '2.0'
29
+ version: '2.2'
30
30
  - !ruby/object:Gem::Dependency
31
31
  name: tilt
32
32
  requirement: !ruby/object:Gem::Requirement
@@ -47,14 +47,14 @@ dependencies:
47
47
  requirements:
48
48
  - - '='
49
49
  - !ruby/object:Gem::Version
50
- version: 2.0.8.1
50
+ version: 2.2.0
51
51
  type: :runtime
52
52
  prerelease: false
53
53
  version_requirements: !ruby/object:Gem::Requirement
54
54
  requirements:
55
55
  - - '='
56
56
  - !ruby/object:Gem::Version
57
- version: 2.0.8.1
57
+ version: 2.2.0
58
58
  - !ruby/object:Gem::Dependency
59
59
  name: mustermann
60
60
  requirement: !ruby/object:Gem::Requirement
@@ -75,18 +75,7 @@ email: sinatrarb@googlegroups.com
75
75
  executables: []
76
76
  extensions: []
77
77
  extra_rdoc_files:
78
- - README.de.md
79
- - README.es.md
80
- - README.fr.md
81
- - README.hu.md
82
- - README.ja.md
83
- - README.ko.md
84
- - README.malayalam.md
85
78
  - README.md
86
- - README.pt-br.md
87
- - README.pt-pt.md
88
- - README.ru.md
89
- - README.zh.md
90
79
  - LICENSE
91
80
  files:
92
81
  - ".yardopts"
@@ -112,6 +101,8 @@ files:
112
101
  - SECURITY.md
113
102
  - VERSION
114
103
  - examples/chat.rb
104
+ - examples/rainbows.conf
105
+ - examples/rainbows.rb
115
106
  - examples/simple.rb
116
107
  - examples/stream.ru
117
108
  - lib/sinatra.rb
@@ -136,7 +127,6 @@ metadata:
136
127
  post_install_message:
137
128
  rdoc_options:
138
129
  - "--line-numbers"
139
- - "--inline-source"
140
130
  - "--title"
141
131
  - Sinatra
142
132
  - "--main"
@@ -148,15 +138,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
148
138
  requirements:
149
139
  - - ">="
150
140
  - !ruby/object:Gem::Version
151
- version: 2.2.0
141
+ version: 2.3.0
152
142
  required_rubygems_version: !ruby/object:Gem::Requirement
153
143
  requirements:
154
144
  - - ">="
155
145
  - !ruby/object:Gem::Version
156
146
  version: '0'
157
147
  requirements: []
158
- rubyforge_project:
159
- rubygems_version: 2.7.3
148
+ rubygems_version: 3.1.2
160
149
  signing_key:
161
150
  specification_version: 4
162
151
  summary: Classy web-development dressed in a DSL