roda 3.0.0 → 3.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: b7717dcab195a4aa608a95fe1b957a4e70e46eb1
4
- data.tar.gz: a183e023f32c278e5ddce68390775ef396472d44
3
+ metadata.gz: d0f2116bac0848dc9f1f4563daab14474e62a79b
4
+ data.tar.gz: 5f564ae0dc012ae84af1a9d5d64c1b4bb214b7b0
5
5
  SHA512:
6
- metadata.gz: 0aded27e4b6f521e554f49d14e805fe3bdf03265f3cb4b4437145bc8767ef4b07ced8e267caaee331dc8fba84cb706c166776dd507e5ff254238c9b39984a94a
7
- data.tar.gz: 79cc0eeea440e916f31b5312c0005e06a543f29204b6ec4b3a34340a221708fb5779b85b38d1242bca29d9b86e789803336e502621bec68034e08e583e1df2b1
6
+ metadata.gz: 31621a2f3576447f261cad0d53ec12b24d407b3f929fbe51be8c102ca279492cc3f19bf80ded152e4b4018fc4f02836b70a5800cbbe39f2fc196e001307e4f6d
7
+ data.tar.gz: b9ede292a9c37c68532b0068fcd79a5d942da3f9b31e751f9ba360df8bcc4959eb35908bcbb06a6389fd93f593b60a80f48537a00e92d76938241799e5e1426a
data/CHANGELOG CHANGED
@@ -1,3 +1,13 @@
1
+ = 3.1.0 (2017-10-13)
2
+
3
+ * Make set_layout_locals and set_view_locals in branch_locals plugin work when the other is not called (jeremyevans)
4
+
5
+ * Add :timestamp_paths option to assets plugin to include timestamps in paths in non-compiled mode (jeremyevans)
6
+
7
+ * Handle ExecJS::RuntimeUnavailable when testing for javascript compression support using uglifier (jeremyevans)
8
+
9
+ * Remove deprecated Roda.thread_safe_cache and RodaRequest#placeholder_string_matcher? methods (jeremyevans)
10
+
1
11
  = 3.0.0 (2017-09-15)
2
12
 
3
13
  * Make defined symbol_matcher and hash_matcher match methods private (jeremyevans)
@@ -443,7 +443,7 @@ treat it as one route with an optional segment. One simple way to do that is to
443
443
  use a parameter instead of an optional segment (e.g. +/items/123?opt=456+).
444
444
 
445
445
  r.is "items", Integer do |item_id|
446
- optional_data = r['opt']
446
+ optional_data = r.params['opt']
447
447
  end
448
448
 
449
449
  However, if you really do want to use a optional segment, there are a couple different
@@ -0,0 +1,24 @@
1
+ = New Features
2
+
3
+ * A :timestamp_paths option has been added to the assets plugin to
4
+ include timestamps in paths in non-compiled mode. This can fix
5
+ asset staleness issues when using a caching proxy. This is
6
+ not needed in compiled mode, as the asset file names include the
7
+ hash of the asset. It is not the default in non-compiled mode,
8
+ as few people would use a caching proxy in non-compiled mode.
9
+
10
+ = Other Improvements
11
+
12
+ * Make set_layout_locals and set_view_locals in branch_locals
13
+ plugin work when the other is not called.
14
+
15
+ * When testing support for uglifier usability as a JS asset
16
+ compressor, handle case where uglifier is installed but there is
17
+ no available javascript runtime.
18
+
19
+ = Backwards Compatibility
20
+
21
+ * The deprecated Roda.thread_safe_cache method has been removed.
22
+
23
+ * The deprecated private RodaRequest#placeholder_string_matcher?
24
+ method has been removed.
@@ -225,13 +225,6 @@ class Roda
225
225
  build_rack_app
226
226
  end
227
227
 
228
- def thread_safe_cache
229
- # :nocov:
230
- RodaPlugins.warn "Roda.thread_safe_cache is deprecated and will be removed from Roda 3.1."
231
- RodaCache.new
232
- # :nocov:
233
- end
234
-
235
228
  # Add a middleware to use for the rack application. Must be
236
229
  # called before calling #route to have an effect. Example:
237
230
  #
@@ -897,15 +890,6 @@ class Roda
897
890
  end
898
891
  end
899
892
 
900
- # Whether string matchers are used verbatim, without handling
901
- # placeholders via colons.
902
- def placeholder_string_matcher?
903
- # :nocov:
904
- RodaPlugins.warn "Roda::RodaRequest.placeholder_string_matcher? is deprecated and will be removed from Roda 3.1."
905
- false
906
- # :nocov:
907
- end
908
-
909
893
  # Handle an unsupported matcher.
910
894
  def unsupported_matcher(matcher)
911
895
  raise RodaError, "unsupported matcher: #{matcher.inspect}"
@@ -294,6 +294,10 @@ class Roda
294
294
  # :sha256, :sha384, or :sha512 depending on which hash algorithm you want to use. This changes the
295
295
  # hash algorithm that Roda will use when naming compiled asset files. The default is :sha256, you
296
296
  # can use nil to disable subresource integrity.
297
+ # :timestamp_paths :: Include the timestamp of assets in asset paths in non-compiled mode. Doing this can
298
+ # slow down development requests due to additional requests to get last modified times,
299
+ # put it will make sure the paths change in development when there are modifications,
300
+ # which can fix issues when using a caching proxy in non-compiled mode.
297
301
  module Assets
298
302
  DEFAULTS = {
299
303
  :compiled_name => 'app'.freeze,
@@ -303,6 +307,7 @@ class Roda
303
307
  :concat_only => false,
304
308
  :compiled => false,
305
309
  :add_suffix => false,
310
+ :timestamp_paths => false,
306
311
  :group_subdirs => true,
307
312
  :compiled_css_dir => nil,
308
313
  :compiled_js_dir => nil,
@@ -556,7 +561,12 @@ class Roda
556
561
 
557
562
  # Compress the JS using Uglifier, requires javascript runtime
558
563
  def compress_js_uglifier(content)
559
- require 'uglifier'
564
+ begin
565
+ require 'uglifier'
566
+ rescue => e
567
+ raise CompressorNotFound, "#{e.class}: #{e.message}", e.backtrace
568
+ end
569
+
560
570
  Uglifier.compile(content)
561
571
  end
562
572
 
@@ -610,7 +620,7 @@ class Roda
610
620
  dirs.each{|f| asset_dir = asset_dir[f]}
611
621
  prefix = "#{dirs.join('/')}/" if o[:group_subdirs]
612
622
  end
613
- Array(asset_dir).map{|f| "#{url_prefix}/#{o[:"#{stype}_prefix"]}#{prefix}#{f}#{o[:"#{stype}_suffix"]}"}
623
+ Array(asset_dir).map{|f| "#{url_prefix}/#{o[:"#{stype}_prefix"]}#{"#{asset_last_modified(File.join(o[:"#{stype}_path"], *[prefix, f].compact)).to_i}/" if o[:timestamp_paths]}#{prefix}#{f}#{o[:"#{stype}_suffix"]}"}
614
624
  end
615
625
  end
616
626
 
@@ -755,7 +765,7 @@ class Roda
755
765
  /#{o[:"compiled_#{type}_prefix"]}(#{Regexp.union(assets)})/
756
766
  else
757
767
  assets = unnest_assets_hash(o[type])
758
- /#{o[:"#{type}_prefix"]}(#{Regexp.union(assets.uniq)})#{o[:"#{type}_suffix"]}/
768
+ /#{o[:"#{type}_prefix"]}#{"\\d+\/" if o[:timestamp_paths]}(#{Regexp.union(assets.uniq)})#{o[:"#{type}_suffix"]}/
759
769
  end
760
770
  end
761
771
 
@@ -60,7 +60,7 @@ class Roda
60
60
  # Make branch specific layout locals override render_locals plugin defaults.
61
61
  def layout_locals
62
62
  locals = super
63
- if @_view_locals
63
+ if @_layout_locals
64
64
  locals = Hash[locals].merge!(@_layout_locals)
65
65
  end
66
66
  locals
@@ -35,7 +35,9 @@ class Roda
35
35
  #
36
36
  # It is possible to use the Roda app as a regular app even when using
37
37
  # the middleware plugin. Using an app as middleware automatically creates
38
- # a subclass of the app for the middleware.
38
+ # a subclass of the app for the middleware. Because a subclass is automatically
39
+ # created when the app is used as middleware, any configuration of the app
40
+ # should be done before using it as middleware instead of after.
39
41
  #
40
42
  # You can support configurable middleware by passing a block when loading
41
43
  # the plugin:
@@ -11,15 +11,29 @@ class Roda
11
11
  # The public plugin recognizes the application's :root option, and defaults to
12
12
  # using the +public+ subfolder of the application's +:root+ option. If the application's
13
13
  # :root option is not set, it defaults to the +public+ folder in the working
14
- # directory. Additionally, if a relative path is provided as the :root
14
+ # directory. Additionally, if a relative path is provided as the +:root+
15
15
  # option to the plugin, it will be considered relative to the application's
16
16
  # +:root+ option.
17
17
  #
18
18
  # Examples:
19
19
  #
20
- # opts[:root] = '/path/to/app'
20
+ # # Use public folder as location of files
21
21
  # plugin :public
22
+ #
23
+ # # Use /path/to/app/static as location of files
24
+ # opts[:root] = '/path/to/app'
22
25
  # plugin :public, root: 'static'
26
+ #
27
+ # # Assuming public is the location of files
28
+ # r.route do
29
+ # # Make GET /images/foo.png look for public/images/foo.png
30
+ # r.public
31
+ #
32
+ # # Make GET /static/images/foo.png look for public/images/foo.png
33
+ # r.on(:static) do
34
+ # r.public
35
+ # end
36
+ # end
23
37
  module Public
24
38
  SPLIT = Regexp.union(*[File::SEPARATOR, File::ALT_SEPARATOR].compact)
25
39
  PARSER = URI::DEFAULT_PARSER
@@ -27,7 +27,7 @@ class Roda
27
27
  # /a :: HTML, JSON, or XML response, depending on the Accept header
28
28
  #
29
29
  # The response +Content-Type+ header will be set to a suitable value when
30
- # the block is matched.
30
+ # the +r.html+, +r.json+, or +r.xml+ block is matched.
31
31
  #
32
32
  # Note that if no match is found, code will continue to execute, which can
33
33
  # result in unexpected behaviour. This should only happen if you do not
@@ -44,7 +44,11 @@ class Roda
44
44
  # end
45
45
  # end
46
46
  #
47
- # This works correctly because Roda assumes the html type by default.
47
+ # This works correctly because Roda's default Content-Type is text/html. Note that
48
+ # if you use this approach, the type_routing plugin's :html content type will not be
49
+ # used for html responses, since you aren't using an +r.html+ block. Instead, the
50
+ # Content-Type header will be set to Roda's default (which you can override via
51
+ # the default_headers plugin).
48
52
  #
49
53
  # To match custom extensions, use the :types option:
50
54
  #
@@ -4,7 +4,7 @@ class Roda
4
4
  RodaMajorVersion = 3
5
5
 
6
6
  # The minor version of Roda, updated for new feature releases of Roda.
7
- RodaMinorVersion = 0
7
+ RodaMinorVersion = 1
8
8
 
9
9
  # The patch version of Roda, updated only for bug fixes from the last
10
10
  # feature release.
@@ -180,7 +180,23 @@ if run_tests
180
180
  js.must_include('console.log')
181
181
  end
182
182
 
183
- it 'should handle rendering assets, linking to them, and accepting requests for them when :add_script_name app option is used' do
183
+ it 'should handle rendering assets, linking to them, and accepting requests for them when :timestamp_paths plugin option is used' do
184
+ app.plugin :assets, :timestamp_paths=>true
185
+ html = body('/test')
186
+ html.scan(/<link/).length.must_equal 2
187
+ html =~ %r{href="(/assets/css/\d+/app\.scss)"}
188
+ css = body($1)
189
+ html =~ %r{href="(/assets/css/\d+/raw\.css)"}
190
+ css2 = body($1)
191
+ html.scan(/<script/).length.must_equal 1
192
+ html =~ %r{src="(/assets/js/\d+/head/app\.js)"}
193
+ js = body($1)
194
+ css.must_match(/color: red;/)
195
+ css2.must_match(/color: blue;/)
196
+ js.must_include('console.log')
197
+ end
198
+
199
+ it 'should handle rendering assets, linking to them, and accepting requests for them when :add_script_name app option is used' do
184
200
  app.opts[:add_script_name] = true
185
201
  app.plugin :assets
186
202
  html = body('/test', 'SCRIPT_NAME'=>'/foo')
@@ -17,6 +17,24 @@ describe "branch_locals plugin" do
17
17
  body.strip.must_equal "<title>Alternative Layout: Home</title>\n<h1>About Roda</h1>"
18
18
  end
19
19
 
20
+ it "should have set_view_locals work without set_layout_locals" do
21
+ app(:branch_locals) do
22
+ set_view_locals :title=>'About Roda'
23
+ view(:inline=>'<h1><%= title %></h1>', :layout=>{:inline=>"<title>Alternative Layout: <%= title %></title>\n<%= yield %>", :locals=>{:title=>'Home'}})
24
+ end
25
+
26
+ body.strip.must_equal "<title>Alternative Layout: Home</title>\n<h1>About Roda</h1>"
27
+ end
28
+
29
+ it "should have set_layout_locals work without set_view_locals" do
30
+ app(:branch_locals) do
31
+ set_layout_locals :title=>'Home'
32
+ view(:inline=>'<h1><%= title %></h1>', :locals=>{:title=>'About Roda'}, :layout=>{:inline=>"<title>Alternative Layout: <%= title %></title>\n<%= yield %>"})
33
+ end
34
+
35
+ body.strip.must_equal "<title>Alternative Layout: Home</title>\n<h1>About Roda</h1>"
36
+ end
37
+
20
38
  it "should merge multiple calls to set view and layout locals" do
21
39
  app(:branch_locals) do
22
40
  set_layout_locals :title=>'About Roda'
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: roda
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.0.0
4
+ version: 3.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Jeremy Evans
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2017-09-15 00:00:00.000000000 Z
11
+ date: 2017-10-13 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rack
@@ -196,6 +196,7 @@ extra_rdoc_files:
196
196
  - doc/release_notes/2.28.0.txt
197
197
  - doc/release_notes/2.29.0.txt
198
198
  - doc/release_notes/3.0.0.txt
199
+ - doc/release_notes/3.1.0.txt
199
200
  files:
200
201
  - CHANGELOG
201
202
  - MIT-LICENSE
@@ -238,6 +239,7 @@ files:
238
239
  - doc/release_notes/2.8.0.txt
239
240
  - doc/release_notes/2.9.0.txt
240
241
  - doc/release_notes/3.0.0.txt
242
+ - doc/release_notes/3.1.0.txt
241
243
  - lib/roda.rb
242
244
  - lib/roda/plugins/_symbol_regexp_matchers.rb
243
245
  - lib/roda/plugins/all_verbs.rb