sinatra 1.4.8 → 2.0.8.1

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.

Files changed (129) hide show
  1. checksums.yaml +5 -5
  2. data/AUTHORS.md +1 -0
  3. data/CHANGELOG.md +238 -54
  4. data/CONTRIBUTING.md +8 -8
  5. data/Gemfile +47 -47
  6. data/LICENSE +4 -1
  7. data/MAINTENANCE.md +42 -0
  8. data/README.de.md +650 -442
  9. data/README.es.md +738 -357
  10. data/README.fr.md +15 -15
  11. data/README.hu.md +37 -3
  12. data/README.ja.md +124 -66
  13. data/README.ko.md +14 -14
  14. data/README.malayalam.md +3141 -0
  15. data/README.md +530 -403
  16. data/README.pt-br.md +2361 -334
  17. data/README.pt-pt.md +2 -2
  18. data/README.ru.md +856 -607
  19. data/README.zh.md +90 -28
  20. data/Rakefile +77 -51
  21. data/SECURITY.md +35 -0
  22. data/VERSION +1 -0
  23. data/lib/sinatra/base.rb +177 -239
  24. data/lib/sinatra/indifferent_hash.rb +200 -0
  25. data/lib/sinatra/main.rb +30 -10
  26. data/lib/sinatra/show_exceptions.rb +102 -62
  27. data/lib/sinatra/version.rb +1 -1
  28. data/sinatra.gemspec +44 -8
  29. metadata +41 -166
  30. data/lib/sinatra/ext.rb +0 -17
  31. data/test/asciidoctor_test.rb +0 -72
  32. data/test/base_test.rb +0 -167
  33. data/test/builder_test.rb +0 -91
  34. data/test/coffee_test.rb +0 -96
  35. data/test/compile_test.rb +0 -183
  36. data/test/contest.rb +0 -91
  37. data/test/creole_test.rb +0 -65
  38. data/test/delegator_test.rb +0 -160
  39. data/test/encoding_test.rb +0 -20
  40. data/test/erb_test.rb +0 -116
  41. data/test/extensions_test.rb +0 -98
  42. data/test/filter_test.rb +0 -487
  43. data/test/haml_test.rb +0 -109
  44. data/test/helper.rb +0 -132
  45. data/test/helpers_test.rb +0 -1917
  46. data/test/integration/app.rb +0 -79
  47. data/test/integration_helper.rb +0 -236
  48. data/test/integration_test.rb +0 -104
  49. data/test/less_test.rb +0 -69
  50. data/test/liquid_test.rb +0 -77
  51. data/test/mapped_error_test.rb +0 -285
  52. data/test/markaby_test.rb +0 -80
  53. data/test/markdown_test.rb +0 -85
  54. data/test/mediawiki_test.rb +0 -68
  55. data/test/middleware_test.rb +0 -68
  56. data/test/nokogiri_test.rb +0 -67
  57. data/test/public/favicon.ico +0 -0
  58. data/test/public/hello+world.txt +0 -1
  59. data/test/rabl_test.rb +0 -89
  60. data/test/rack_test.rb +0 -45
  61. data/test/radius_test.rb +0 -59
  62. data/test/rdoc_test.rb +0 -66
  63. data/test/readme_test.rb +0 -130
  64. data/test/request_test.rb +0 -100
  65. data/test/response_test.rb +0 -63
  66. data/test/result_test.rb +0 -76
  67. data/test/route_added_hook_test.rb +0 -59
  68. data/test/routing_test.rb +0 -1456
  69. data/test/sass_test.rb +0 -115
  70. data/test/scss_test.rb +0 -88
  71. data/test/server_test.rb +0 -56
  72. data/test/settings_test.rb +0 -582
  73. data/test/sinatra_test.rb +0 -12
  74. data/test/slim_test.rb +0 -102
  75. data/test/static_test.rb +0 -266
  76. data/test/streaming_test.rb +0 -149
  77. data/test/stylus_test.rb +0 -90
  78. data/test/templates_test.rb +0 -382
  79. data/test/textile_test.rb +0 -65
  80. data/test/views/a/in_a.str +0 -1
  81. data/test/views/ascii.erb +0 -2
  82. data/test/views/b/in_b.str +0 -1
  83. data/test/views/calc.html.erb +0 -1
  84. data/test/views/error.builder +0 -3
  85. data/test/views/error.erb +0 -3
  86. data/test/views/error.haml +0 -3
  87. data/test/views/error.sass +0 -2
  88. data/test/views/explicitly_nested.str +0 -1
  89. data/test/views/foo/hello.test +0 -1
  90. data/test/views/hello.asciidoc +0 -1
  91. data/test/views/hello.builder +0 -1
  92. data/test/views/hello.coffee +0 -1
  93. data/test/views/hello.creole +0 -1
  94. data/test/views/hello.erb +0 -1
  95. data/test/views/hello.haml +0 -1
  96. data/test/views/hello.less +0 -5
  97. data/test/views/hello.liquid +0 -1
  98. data/test/views/hello.mab +0 -1
  99. data/test/views/hello.md +0 -1
  100. data/test/views/hello.mediawiki +0 -1
  101. data/test/views/hello.nokogiri +0 -1
  102. data/test/views/hello.rabl +0 -2
  103. data/test/views/hello.radius +0 -1
  104. data/test/views/hello.rdoc +0 -1
  105. data/test/views/hello.sass +0 -2
  106. data/test/views/hello.scss +0 -3
  107. data/test/views/hello.slim +0 -1
  108. data/test/views/hello.str +0 -1
  109. data/test/views/hello.styl +0 -2
  110. data/test/views/hello.test +0 -1
  111. data/test/views/hello.textile +0 -1
  112. data/test/views/hello.wlang +0 -1
  113. data/test/views/hello.yajl +0 -1
  114. data/test/views/layout2.builder +0 -3
  115. data/test/views/layout2.erb +0 -2
  116. data/test/views/layout2.haml +0 -2
  117. data/test/views/layout2.liquid +0 -2
  118. data/test/views/layout2.mab +0 -2
  119. data/test/views/layout2.nokogiri +0 -3
  120. data/test/views/layout2.rabl +0 -3
  121. data/test/views/layout2.radius +0 -2
  122. data/test/views/layout2.slim +0 -3
  123. data/test/views/layout2.str +0 -2
  124. data/test/views/layout2.test +0 -1
  125. data/test/views/layout2.wlang +0 -2
  126. data/test/views/nested.str +0 -1
  127. data/test/views/utf8.erb +0 -2
  128. data/test/wlang_test.rb +0 -87
  129. data/test/yajl_test.rb +0 -86
@@ -0,0 +1,200 @@
1
+ # frozen_string_literal: true
2
+ $stderr.puts <<EOF if !Hash.method_defined?(:slice) && !$LOAD_PATH.grep(%r{gems/activesupport}).empty? && ENV['SINATRA_ACTIVESUPPORT_WARNING'] != 'false'
3
+ WARNING: If you plan to load any of ActiveSupport's core extensions to Hash, be
4
+ sure to do so *before* loading Sinatra::Application or Sinatra::Base. If not,
5
+ you may disregard this warning.
6
+
7
+ Set SINATRA_ACTIVESUPPORT_WARNING=false in the environment to hide this warning.
8
+ EOF
9
+
10
+ module Sinatra
11
+ # A poor man's ActiveSupport::HashWithIndifferentAccess, with all the Rails-y
12
+ # stuff removed.
13
+ #
14
+ # Implements a hash where keys <tt>:foo</tt> and <tt>"foo"</tt> are
15
+ # considered to be the same.
16
+ #
17
+ # rgb = Sinatra::IndifferentHash.new
18
+ #
19
+ # rgb[:black] = '#000000' # symbol assignment
20
+ # rgb[:black] # => '#000000' # symbol retrieval
21
+ # rgb['black'] # => '#000000' # string retrieval
22
+ #
23
+ # rgb['white'] = '#FFFFFF' # string assignment
24
+ # rgb[:white] # => '#FFFFFF' # symbol retrieval
25
+ # rgb['white'] # => '#FFFFFF' # string retrieval
26
+ #
27
+ # Internally, symbols are mapped to strings when used as keys in the entire
28
+ # writing interface (calling e.g. <tt>[]=</tt>, <tt>merge</tt>). This mapping
29
+ # belongs to the public interface. For example, given:
30
+ #
31
+ # hash = Sinatra::IndifferentHash.new(:a=>1)
32
+ #
33
+ # You are guaranteed that the key is returned as a string:
34
+ #
35
+ # hash.keys # => ["a"]
36
+ #
37
+ # Technically other types of keys are accepted:
38
+ #
39
+ # hash = Sinatra::IndifferentHash.new(:a=>1)
40
+ # hash[0] = 0
41
+ # hash # => { "a"=>1, 0=>0 }
42
+ #
43
+ # But this class is intended for use cases where strings or symbols are the
44
+ # expected keys and it is convenient to understand both as the same. For
45
+ # example the +params+ hash in Sinatra.
46
+ class IndifferentHash < Hash
47
+ def self.[](*args)
48
+ new.merge!(Hash[*args])
49
+ end
50
+
51
+ def initialize(*args)
52
+ args.map!(&method(:convert_value))
53
+
54
+ super(*args)
55
+ end
56
+
57
+ def default(*args)
58
+ args.map!(&method(:convert_key))
59
+
60
+ super(*args)
61
+ end
62
+
63
+ def default=(value)
64
+ super(convert_value(value))
65
+ end
66
+
67
+ def assoc(key)
68
+ super(convert_key(key))
69
+ end
70
+
71
+ def rassoc(value)
72
+ super(convert_value(value))
73
+ end
74
+
75
+ def fetch(key, *args)
76
+ args.map!(&method(:convert_value))
77
+
78
+ super(convert_key(key), *args)
79
+ end
80
+
81
+ def [](key)
82
+ super(convert_key(key))
83
+ end
84
+
85
+ def []=(key, value)
86
+ super(convert_key(key), convert_value(value))
87
+ end
88
+
89
+ alias_method :store, :[]=
90
+
91
+ def key(value)
92
+ super(convert_value(value))
93
+ end
94
+
95
+ def key?(key)
96
+ super(convert_key(key))
97
+ end
98
+
99
+ alias_method :has_key?, :key?
100
+ alias_method :include?, :key?
101
+ alias_method :member?, :key?
102
+
103
+ def value?(value)
104
+ super(convert_value(value))
105
+ end
106
+
107
+ alias_method :has_value?, :value?
108
+
109
+ def delete(key)
110
+ super(convert_key(key))
111
+ end
112
+
113
+ def dig(key, *other_keys)
114
+ super(convert_key(key), *other_keys)
115
+ end if method_defined?(:dig) # Added in Ruby 2.3
116
+
117
+ def fetch_values(*keys)
118
+ keys.map!(&method(:convert_key))
119
+
120
+ super(*keys)
121
+ end if method_defined?(:fetch_values) # Added in Ruby 2.3
122
+
123
+ def slice(*keys)
124
+ keys.map!(&method(:convert_key))
125
+
126
+ self.class[super(*keys)]
127
+ end if method_defined?(:slice) # Added in Ruby 2.5
128
+
129
+ def values_at(*keys)
130
+ keys.map!(&method(:convert_key))
131
+
132
+ super(*keys)
133
+ end
134
+
135
+ def merge!(*other_hashes)
136
+ other_hashes.each do |other_hash|
137
+ if other_hash.is_a?(self.class)
138
+ super(other_hash)
139
+ else
140
+ other_hash.each_pair do |key, value|
141
+ key = convert_key(key)
142
+ value = yield(key, self[key], value) if block_given? && key?(key)
143
+ self[key] = convert_value(value)
144
+ end
145
+ end
146
+ end
147
+
148
+ self
149
+ end
150
+
151
+ alias_method :update, :merge!
152
+
153
+ def merge(*other_hashes, &block)
154
+ dup.merge!(*other_hashes, &block)
155
+ end
156
+
157
+ def replace(other_hash)
158
+ super(other_hash.is_a?(self.class) ? other_hash : self.class[other_hash])
159
+ end
160
+
161
+ if method_defined?(:transform_values!) # Added in Ruby 2.4
162
+ def transform_values(&block)
163
+ dup.transform_values!(&block)
164
+ end
165
+
166
+ def transform_values!
167
+ super
168
+ super(&method(:convert_value))
169
+ end
170
+ end
171
+
172
+ if method_defined?(:transform_keys!) # Added in Ruby 2.5
173
+ def transform_keys(&block)
174
+ dup.transform_keys!(&block)
175
+ end
176
+
177
+ def transform_keys!
178
+ super
179
+ super(&method(:convert_key))
180
+ end
181
+ end
182
+
183
+ private
184
+
185
+ def convert_key(key)
186
+ key.is_a?(Symbol) ? key.to_s : key
187
+ end
188
+
189
+ def convert_value(value)
190
+ case value
191
+ when Hash
192
+ value.is_a?(self.class) ? value : self.class[value]
193
+ when Array
194
+ value.map(&method(:convert_value))
195
+ else
196
+ value
197
+ end
198
+ end
199
+ end
200
+ end
data/lib/sinatra/main.rb CHANGED
@@ -1,6 +1,30 @@
1
- require 'sinatra/base'
2
-
3
1
  module Sinatra
2
+ ParamsConfig = {}
3
+
4
+ if ARGV.any?
5
+ require 'optparse'
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|
12
+ ENV['RACK_ENV'] = val
13
+ ParamsConfig[:environment] = val.to_sym
14
+ end
15
+ op.on('-o addr', "set the host (default is (env == 'development' ? 'localhost' : '0.0.0.0'))") do |val|
16
+ ParamsConfig[:bind] = val
17
+ end
18
+ }
19
+ begin
20
+ parser.parse!(ARGV.dup)
21
+ rescue => evar
22
+ ParamsConfig[:optparse_error] = evar
23
+ end
24
+ end
25
+
26
+ require 'sinatra/base'
27
+
4
28
  class Application < Base
5
29
 
6
30
  # we assume that the first file that requires 'sinatra' is the
@@ -11,17 +35,13 @@ module Sinatra
11
35
  set :run, Proc.new { File.expand_path($0) == File.expand_path(app_file) }
12
36
 
13
37
  if run? && ARGV.any?
14
- require 'optparse'
15
- OptionParser.new { |op|
16
- op.on('-p port', 'set the port (default is 4567)') { |val| set :port, Integer(val) }
17
- op.on('-o addr', "set the host (default is #{bind})") { |val| set :bind, val }
18
- op.on('-e env', 'set the environment (default is development)') { |val| set :environment, val.to_sym }
19
- op.on('-s server', 'specify rack server/handler (default is thin)') { |val| set :server, val }
20
- op.on('-x', 'turn on the mutex lock (default is off)') { set :lock, true }
21
- }.parse!(ARGV.dup)
38
+ error = ParamsConfig.delete(:optparse_error)
39
+ raise error if error
40
+ ParamsConfig.each { |k, v| set k, v }
22
41
  end
23
42
  end
24
43
 
44
+ remove_const(:ParamsConfig)
25
45
  at_exit { Application.run! if $!.nil? && Application.run? }
26
46
  end
27
47
 
@@ -1,8 +1,6 @@
1
- begin
2
- require 'rack/show_exceptions'
3
- rescue LoadError
4
- require 'rack/showexceptions'
5
- end
1
+ # frozen_string_literal: true
2
+
3
+ require 'rack/show_exceptions'
6
4
 
7
5
  module Sinatra
8
6
  # Sinatra::ShowExceptions catches all exceptions raised from the app it
@@ -17,8 +15,7 @@ module Sinatra
17
15
  def @@eats_errors.puts(*) end
18
16
 
19
17
  def initialize(app)
20
- @app = app
21
- @template = ERB.new(TEMPLATE)
18
+ @app = app
22
19
  end
23
20
 
24
21
  def call(env)
@@ -28,47 +25,86 @@ module Sinatra
28
25
 
29
26
  if prefers_plain_text?(env)
30
27
  content_type = "text/plain"
31
- exception = dump_exception(e)
28
+ body = dump_exception(e)
32
29
  else
33
30
  content_type = "text/html"
34
- exception = pretty(env, e)
31
+ body = pretty(env, e)
35
32
  end
36
33
 
37
34
  env["rack.errors"] = errors
38
35
 
39
- # Post 893a2c50 in rack/rack, the #pretty method above, implemented in
40
- # Rack::ShowExceptions, returns a String instead of an array.
41
- body = Array(exception)
42
-
43
36
  [
44
37
  500,
45
38
  {
46
39
  "Content-Type" => content_type,
47
- "Content-Length" => Rack::Utils.bytesize(body.join).to_s
40
+ "Content-Length" => body.bytesize.to_s
48
41
  },
49
- body
42
+ [body]
50
43
  ]
51
44
  end
52
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)
83
+ end
84
+
53
85
  private
54
86
 
87
+ def bad_request?(e)
88
+ Sinatra::BadRequest === e
89
+ end
90
+
55
91
  def prefers_plain_text?(env)
56
92
  !(Request.new(env).preferred_type("text/plain","text/html") == "text/html") &&
57
- [/curl/].index{|item| item =~ env["HTTP_USER_AGENT"]}
93
+ [/curl/].index { |item| item =~ env["HTTP_USER_AGENT"] }
58
94
  end
59
95
 
60
96
  def frame_class(frame)
61
- if frame.filename =~ /lib\/sinatra.*\.rb/
97
+ if frame.filename =~ %r{lib/sinatra.*\.rb}
62
98
  "framework"
63
99
  elsif (defined?(Gem) && frame.filename.include?(Gem.dir)) ||
64
- frame.filename =~ /\/bin\/(\w+)$/
100
+ frame.filename =~ %r{/bin/(\w+)\z}
65
101
  "system"
66
102
  else
67
103
  "app"
68
104
  end
69
105
  end
70
106
 
71
- TEMPLATE = <<-HTML # :nodoc:
107
+ TEMPLATE = ERB.new <<-HTML # :nodoc:
72
108
  <!DOCTYPE html>
73
109
  <html>
74
110
  <head>
@@ -213,8 +249,10 @@ TEMPLATE = <<-HTML # :nodoc:
213
249
  <p><a href="#" id="expando"
214
250
  onclick="toggleBacktrace(); return false">(expand)</a></p>
215
251
  <p id="nav"><strong>JUMP TO:</strong>
216
- <a href="#get-info">GET</a>
217
- <a href="#post-info">POST</a>
252
+ <% unless bad_request?(exception) %>
253
+ <a href="#get-info">GET</a>
254
+ <a href="#post-info">POST</a>
255
+ <% end %>
218
256
  <a href="#cookie-info">COOKIES</a>
219
257
  <a href="#env-info">ENV</a>
220
258
  </p>
@@ -267,47 +305,49 @@ TEMPLATE = <<-HTML # :nodoc:
267
305
  </ul>
268
306
  </div> <!-- /BACKTRACE -->
269
307
 
270
- <div id="get">
271
- <h3 id="get-info">GET</h3>
272
- <% if req.GET and not req.GET.empty? %>
273
- <table class="req">
274
- <tr>
275
- <th>Variable</th>
276
- <th>Value</th>
277
- </tr>
278
- <% req.GET.sort_by { |k, v| k.to_s }.each { |key, val| %>
279
- <tr>
280
- <td><%=h key %></td>
281
- <td class="code"><div><%=h val.inspect %></div></td>
282
- </tr>
283
- <% } %>
284
- </table>
285
- <% else %>
286
- <p class="no-data">No GET data.</p>
287
- <% end %>
288
- <div class="clear"></div>
289
- </div> <!-- /GET -->
290
-
291
- <div id="post">
292
- <h3 id="post-info">POST</h3>
293
- <% if req.POST and not req.POST.empty? %>
294
- <table class="req">
295
- <tr>
296
- <th>Variable</th>
297
- <th>Value</th>
298
- </tr>
299
- <% req.POST.sort_by { |k, v| k.to_s }.each { |key, val| %>
300
- <tr>
301
- <td><%=h key %></td>
302
- <td class="code"><div><%=h val.inspect %></div></td>
303
- </tr>
304
- <% } %>
305
- </table>
306
- <% else %>
307
- <p class="no-data">No POST data.</p>
308
- <% end %>
309
- <div class="clear"></div>
310
- </div> <!-- /POST -->
308
+ <% unless bad_request?(exception) %>
309
+ <div id="get">
310
+ <h3 id="get-info">GET</h3>
311
+ <% if req.GET and not req.GET.empty? %>
312
+ <table class="req">
313
+ <tr>
314
+ <th>Variable</th>
315
+ <th>Value</th>
316
+ </tr>
317
+ <% req.GET.sort_by { |k, v| k.to_s }.each { |key, val| %>
318
+ <tr>
319
+ <td><%=h key %></td>
320
+ <td class="code"><div><%=h val.inspect %></div></td>
321
+ </tr>
322
+ <% } %>
323
+ </table>
324
+ <% else %>
325
+ <p class="no-data">No GET data.</p>
326
+ <% end %>
327
+ <div class="clear"></div>
328
+ </div> <!-- /GET -->
329
+
330
+ <div id="post">
331
+ <h3 id="post-info">POST</h3>
332
+ <% if req.POST and not req.POST.empty? %>
333
+ <table class="req">
334
+ <tr>
335
+ <th>Variable</th>
336
+ <th>Value</th>
337
+ </tr>
338
+ <% req.POST.sort_by { |k, v| k.to_s }.each { |key, val| %>
339
+ <tr>
340
+ <td><%=h key %></td>
341
+ <td class="code"><div><%=h val.inspect %></div></td>
342
+ </tr>
343
+ <% } %>
344
+ </table>
345
+ <% else %>
346
+ <p class="no-data">No POST data.</p>
347
+ <% end %>
348
+ <div class="clear"></div>
349
+ </div> <!-- /POST -->
350
+ <% end %>
311
351
 
312
352
  <div id="cookies">
313
353
  <h3 id="cookie-info">COOKIES</h3>
@@ -1,3 +1,3 @@
1
1
  module Sinatra
2
- VERSION = '1.4.8'
2
+ VERSION = '2.0.8.1'
3
3
  end
data/sinatra.gemspec CHANGED
@@ -1,19 +1,55 @@
1
- $LOAD_PATH.unshift File.expand_path('../lib', __FILE__)
2
- require 'sinatra/version'
1
+ version = File.read(File.expand_path("../VERSION", __FILE__)).strip
3
2
 
4
- Gem::Specification.new 'sinatra', Sinatra::VERSION do |s|
3
+ Gem::Specification.new 'sinatra', version do |s|
5
4
  s.description = "Sinatra is a DSL for quickly creating web applications in Ruby with minimal effort."
6
5
  s.summary = "Classy web-development dressed in a DSL"
7
6
  s.authors = ["Blake Mizerany", "Ryan Tomayko", "Simon Rozet", "Konstantin Haase"]
8
7
  s.email = "sinatrarb@googlegroups.com"
9
- s.homepage = "http://www.sinatrarb.com/"
8
+ s.homepage = "http://sinatrarb.com/"
10
9
  s.license = 'MIT'
11
- s.files = `git ls-files`.split("\n") - %w[.gitignore .travis.yml]
10
+ s.files = Dir['README*.md', 'lib/**/*', 'examples/*'] + [
11
+ ".yardopts",
12
+ "AUTHORS.md",
13
+ "CHANGELOG.md",
14
+ "CONTRIBUTING.md",
15
+ "Gemfile",
16
+ "LICENSE",
17
+ "MAINTENANCE.md",
18
+ "Rakefile",
19
+ "SECURITY.md",
20
+ "sinatra.gemspec",
21
+ "VERSION"]
12
22
  s.test_files = s.files.select { |p| p =~ /^test\/.*_test.rb/ }
13
23
  s.extra_rdoc_files = s.files.select { |p| p =~ /^README/ } << 'LICENSE'
14
24
  s.rdoc_options = %w[--line-numbers --inline-source --title Sinatra --main README.rdoc --encoding=UTF-8]
15
25
 
16
- s.add_dependency 'rack', '~> 1.5'
17
- s.add_dependency 'tilt', '>= 1.3', '< 3'
18
- s.add_dependency 'rack-protection', '~> 1.4'
26
+ if s.respond_to?(:metadata)
27
+ s.metadata = {
28
+ 'source_code_uri' => 'https://github.com/sinatra/sinatra',
29
+ 'changelog_uri' => 'https://github.com/sinatra/sinatra/blob/master/CHANGELOG.md',
30
+ 'homepage_uri' => 'http://sinatrarb.com/',
31
+ 'bug_tracker_uri' => 'https://github.com/sinatra/sinatra/issues',
32
+ 'mailing_list_uri' => 'http://groups.google.com/group/sinatrarb',
33
+ 'documentation_uri' => 'https://www.rubydoc.info/gems/sinatra'
34
+ }
35
+ 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
+ raise <<-EOF
42
+ RubyGems 2.0 or newer is required to protect against public gem pushes. You can update your rubygems version by running:
43
+ gem install rubygems-update
44
+ update_rubygems:
45
+ gem update --system
46
+ EOF
47
+ end
48
+
49
+ s.required_ruby_version = '>= 2.2.0'
50
+
51
+ s.add_dependency 'rack', '~> 2.0'
52
+ s.add_dependency 'tilt', '~> 2.0'
53
+ s.add_dependency 'rack-protection', version
54
+ s.add_dependency 'mustermann', '~> 1.0'
19
55
  end