middleman-core 4.0.0.alpha.6 → 4.0.0.beta.1

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.
Files changed (83) hide show
  1. checksums.yaml +4 -4
  2. data/features/asset_hash.feature +8 -1
  3. data/features/asset_host.feature +2 -13
  4. data/features/builder.feature +0 -2
  5. data/features/cli_init.feature +32 -0
  6. data/features/collections.feature +50 -0
  7. data/features/directory_index.feature +4 -5
  8. data/features/front-matter-neighbor.feature +20 -0
  9. data/features/helpers_link_to.feature +18 -0
  10. data/features/image_srcset_paths.feature +7 -0
  11. data/features/markdown_kramdown_in_haml.feature +2 -1
  12. data/features/minify_javascript.feature +1 -1
  13. data/features/multiple-sources.feature +8 -0
  14. data/fixtures/asset-hash-app/source/slim.html.slim +8 -0
  15. data/fixtures/asset-hash-app/source/subdir/index.html.erb +10 -1
  16. data/fixtures/asset-host-app/source/asset_host.html.erb +23 -1
  17. data/fixtures/collections-app/source/blog2/2011-01-01-new-article.html.markdown +2 -0
  18. data/fixtures/frontmatter-settings-neighbor-app/config.rb +19 -14
  19. data/fixtures/image-srcset-paths-app/image-srcset-paths.html.erb +1 -0
  20. data/fixtures/image-srcset-paths-app/images/blank.gif +0 -0
  21. data/fixtures/indexable-app/source/evil spaces.html +1 -1
  22. data/fixtures/large-build-app/config.rb +2 -0
  23. data/fixtures/large-build-app/source/spaces in file.html.erb +1 -1
  24. data/fixtures/more-traversal-app/source/layout.erb +1 -1
  25. data/fixtures/multiple-sources-with-duplicate-file-names-app/config.rb +2 -0
  26. data/fixtures/multiple-sources-with-duplicate-file-names-app/source/index.html.erb +1 -0
  27. data/fixtures/multiple-sources-with-duplicate-file-names-app/source2/index.html.erb +1 -0
  28. data/fixtures/traversal-app/source/.htaccess +0 -0
  29. data/fixtures/traversal-app/source/layout.erb +1 -1
  30. data/lib/middleman/rack.rb +1 -0
  31. data/lib/middleman-core/application.rb +15 -15
  32. data/lib/middleman-core/builder.rb +11 -7
  33. data/lib/middleman-core/cli/server.rb +86 -0
  34. data/lib/middleman-core/config_context.rb +1 -1
  35. data/lib/middleman-core/contracts.rb +0 -32
  36. data/lib/middleman-core/core_extensions/collections.rb +19 -17
  37. data/lib/middleman-core/core_extensions/data.rb +15 -17
  38. data/lib/middleman-core/core_extensions/default_helpers.rb +22 -1
  39. data/lib/middleman-core/core_extensions/file_watcher.rb +9 -7
  40. data/lib/middleman-core/core_extensions/front_matter.rb +2 -2
  41. data/lib/middleman-core/core_extensions/i18n.rb +11 -9
  42. data/lib/middleman-core/core_extensions/routing.rb +3 -4
  43. data/lib/middleman-core/extension.rb +179 -0
  44. data/lib/middleman-core/extension_manager.rb +8 -7
  45. data/lib/middleman-core/extensions/asset_hash.rb +14 -9
  46. data/lib/middleman-core/extensions/asset_host.rb +3 -1
  47. data/lib/middleman-core/extensions/gzip.rb +3 -2
  48. data/lib/middleman-core/extensions/lorem.rb +2 -2
  49. data/lib/middleman-core/extensions/relative_assets.rb +11 -5
  50. data/lib/middleman-core/file_renderer.rb +2 -2
  51. data/lib/middleman-core/logger.rb +1 -1
  52. data/lib/middleman-core/middleware/inline_url_rewriter.rb +9 -4
  53. data/lib/middleman-core/preview_server.rb +13 -9
  54. data/lib/middleman-core/rack.rb +2 -1
  55. data/lib/middleman-core/renderers/haml.rb +6 -0
  56. data/lib/middleman-core/renderers/kramdown.rb +1 -1
  57. data/lib/middleman-core/renderers/redcarpet.rb +1 -0
  58. data/lib/middleman-core/renderers/sass.rb +1 -1
  59. data/lib/middleman-core/renderers/slim.rb +1 -0
  60. data/lib/middleman-core/sitemap/extensions/ignores.rb +7 -4
  61. data/lib/middleman-core/sitemap/extensions/on_disk.rb +1 -1
  62. data/lib/middleman-core/sitemap/extensions/proxies.rb +13 -10
  63. data/lib/middleman-core/sitemap/extensions/redirects.rb +8 -7
  64. data/lib/middleman-core/sitemap/extensions/request_endpoints.rb +7 -6
  65. data/lib/middleman-core/sitemap/extensions/traversal.rb +3 -1
  66. data/lib/middleman-core/sitemap/resource.rb +14 -15
  67. data/lib/middleman-core/sitemap/store.rb +6 -5
  68. data/lib/middleman-core/sources/source_watcher.rb +29 -16
  69. data/lib/middleman-core/sources.rb +19 -21
  70. data/lib/middleman-core/step_definitions/builder_steps.rb +1 -1
  71. data/lib/middleman-core/step_definitions/server_steps.rb +3 -3
  72. data/lib/middleman-core/template_context.rb +8 -7
  73. data/lib/middleman-core/template_renderer.rb +2 -2
  74. data/lib/middleman-core/util.rb +57 -21
  75. data/lib/middleman-core/version.rb +1 -1
  76. data/lib/middleman-core.rb +2 -1
  77. data/middleman-core.gemspec +4 -1
  78. data/spec/middleman-core/core_extensions/data_spec.rb +41 -0
  79. data/spec/middleman-core/util_spec.rb +96 -0
  80. metadata +38 -8
  81. data/lib/middleman-core/util/hash_with_indifferent_access.rb +0 -103
  82. data/spec/middleman-core/binary_spec.rb +0 -15
  83. data/spec/middleman-core/path_match_spec.rb +0 -37
@@ -1,9 +1,6 @@
1
1
  # For instrumenting
2
2
  require 'active_support/notifications'
3
3
 
4
- # Indifferent hash access
5
- require 'middleman-core/util/hash_with_indifferent_access'
6
-
7
4
  # Core Pathname library used for traversal
8
5
  require 'pathname'
9
6
 
@@ -14,7 +11,11 @@ require 'rack/mime'
14
11
  # DbC
15
12
  require 'middleman-core/contracts'
16
13
 
14
+ # Immutable Data
15
+ require 'hamster'
16
+
17
17
  # For URI templating
18
+ require 'addressable/uri'
18
19
  require 'addressable/template'
19
20
  require 'active_support/inflector'
20
21
  require 'active_support/inflector/transliterate'
@@ -75,22 +76,56 @@ module Middleman
75
76
  end
76
77
  end
77
78
 
78
- # Recursively convert a normal Hash into a HashWithIndifferentAccess
79
+ class IndifferentHash < ::Hamster::Hash
80
+ def [](key)
81
+ if key?(key.to_sym)
82
+ super(key.to_sym)
83
+ elsif key?(key.to_s)
84
+ super(key.to_s)
85
+ else
86
+ super
87
+ end
88
+ end
89
+
90
+ def method_missing(key, *_args)
91
+ if key?(key.to_sym)
92
+ self[key.to_sym]
93
+ elsif key?(key.to_s)
94
+ self[key.to_s]
95
+ end
96
+ end
97
+ end
98
+
99
+ # Recursively convert a normal Hash into a IndifferentHash
79
100
  #
80
101
  # @private
81
102
  # @param [Hash] data Normal hash
82
- # @return [Middleman::Util::HashWithIndifferentAccess]
83
- FrozenDataStructure = Frozen[Or[HashWithIndifferentAccess, Array]]
84
- Contract Maybe[Or[Array, Hash, HashWithIndifferentAccess]] => Maybe[FrozenDataStructure]
85
- def recursively_enhance(data)
86
- if data.is_a? HashWithIndifferentAccess
87
- data
88
- elsif data.is_a? Hash
89
- HashWithIndifferentAccess.new(data)
90
- elsif data.is_a? Array
91
- data.map(&method(:recursively_enhance)).freeze
103
+ # @return [Middleman::Util::IndifferentHash]
104
+ FrozenDataStructure = Frozen[Or[IndifferentHash, Array, String, TrueClass, FalseClass, Fixnum, NilClass]]
105
+ Contract Maybe[Or[String, Array, Hash, IndifferentHash]] => Maybe[FrozenDataStructure]
106
+ def recursively_enhance(obj)
107
+ case obj
108
+ when ::Hash
109
+ res = obj.map { |key, value| [recursively_enhance(key), recursively_enhance(value)] }
110
+ IndifferentHash.new(res)
111
+ when IndifferentHash
112
+ obj.map { |key, value| [recursively_enhance(key), recursively_enhance(value)] }
113
+ when ::Array
114
+ res = obj.map { |element| recursively_enhance(element) }
115
+ Hamster::Vector.new(res)
116
+ when ::SortedSet
117
+ # This clause must go before ::Set clause, since ::SortedSet is a ::Set.
118
+ res = obj.map { |element| recursively_enhance(element) }
119
+ Hamster::SortedSet.new(res)
120
+ when ::Set
121
+ res = obj.map { |element| recursively_enhance(element) }
122
+ Hamster::Set.new(res)
123
+ when Hamster::Vector, Hamster::Set, Hamster::SortedSet
124
+ obj.map { |element| recursively_enhance(element) }
125
+ when ::TrueClass, ::FalseClass, ::Fixnum, ::Symbol, ::NilClass
126
+ obj
92
127
  else
93
- nil
128
+ obj.dup.freeze
94
129
  end
95
130
  end
96
131
 
@@ -100,7 +135,7 @@ module Middleman
100
135
  Contract String => String
101
136
  def normalize_path(path)
102
137
  # The tr call works around a bug in Ruby's Unicode handling
103
- path.sub(%r{^/}, '').tr('', '')
138
+ URI.decode(path).sub(%r{^/}, '').tr('', '')
104
139
  end
105
140
 
106
141
  # This is a separate method from normalize_path in case we
@@ -223,7 +258,7 @@ module Middleman
223
258
  path_or_resource.url
224
259
  else
225
260
  path_or_resource.dup
226
- end.gsub(' ', '%20')
261
+ end
227
262
 
228
263
  # Try to parse URL
229
264
  begin
@@ -248,7 +283,7 @@ module Middleman
248
283
  if path_or_resource.is_a?(::Middleman::Sitemap::Resource)
249
284
  resource = path_or_resource
250
285
  resource_url = url
251
- elsif this_resource && uri.path
286
+ elsif this_resource && uri.path && !uri.host
252
287
  # Handle relative urls
253
288
  url_path = Pathname(uri.path)
254
289
  current_source_dir = Pathname('/' + this_resource.path).dirname
@@ -264,14 +299,14 @@ module Middleman
264
299
  resource = app.sitemap.find_resource_by_destination_path(url_path.to_s)
265
300
  resource_url = resource.url if resource
266
301
  end
267
- elsif options[:find_resource] && uri.path
302
+ elsif options[:find_resource] && uri.path && !uri.host
268
303
  resource = app.sitemap.find_resource_by_path(uri.path)
269
304
  resource_url = resource.url if resource
270
305
  end
271
306
 
272
307
  if resource
273
308
  uri.path = if this_resource
274
- relative_path_from_resource(this_resource, resource_url, effective_relative)
309
+ URI.encode(relative_path_from_resource(this_resource, resource_url, effective_relative))
275
310
  else
276
311
  resource_url
277
312
  end
@@ -321,7 +356,8 @@ module Middleman
321
356
  opening_character = $1
322
357
  asset_path = $2
323
358
 
324
- if result = yield(asset_path)
359
+ uri = ::Addressable::URI.parse(asset_path)
360
+ if uri.relative? && result = yield(asset_path)
325
361
  "#{opening_character}#{result}"
326
362
  else
327
363
  match
@@ -1,5 +1,5 @@
1
1
  module Middleman
2
2
  # Current Version
3
3
  # @return [String]
4
- VERSION = '4.0.0.alpha.6' unless const_defined?(:VERSION)
4
+ VERSION = '4.0.0.beta.1' unless const_defined?(:VERSION)
5
5
  end
@@ -8,9 +8,10 @@ $LOAD_PATH.unshift(libdir) unless $LOAD_PATH.include?(libdir)
8
8
  module Middleman
9
9
  # Backwards compatibility namespace
10
10
  module Features; end
11
+
12
+ autoload :Application, 'middleman-core/application'
11
13
  end
12
14
 
13
15
  require 'middleman-core/version'
14
16
  require 'middleman-core/util'
15
17
  require 'middleman-core/extensions'
16
- require 'middleman-core/application'
@@ -51,5 +51,8 @@ Gem::Specification.new do |s|
51
51
  s.add_dependency('execjs', ['~> 2.0'])
52
52
 
53
53
  # Testing
54
- s.add_dependency('contracts', ['~> 0.4'])
54
+ s.add_dependency('contracts', ['~> 0.9.0'])
55
+
56
+ # Immutability
57
+ s.add_dependency('hamster', ['~> 1.0'])
55
58
  end
@@ -0,0 +1,41 @@
1
+ require 'spec_helper'
2
+ require 'middleman-core/core_extensions'
3
+ require 'middleman-core/core_extensions/data'
4
+
5
+ describe Middleman::CoreExtensions::Data do
6
+ end
7
+
8
+ describe Middleman::CoreExtensions::Data::DataStore do
9
+
10
+ describe "#key?" do
11
+
12
+ it "returns true if key included in local_data, local_sources, or callback_sources" do
13
+ subject = described_class.new instance_double("Middleman::Application"), Middleman::CoreExtensions::Data::DATA_FILE_MATCHER
14
+ subject.store :"foo-store", { foo: "bar" }
15
+ subject.callbacks :"foo-callback", Proc.new { "bar" }
16
+ subject.instance_variable_get(:@local_data)["foo-local"] = "bar"
17
+
18
+ expect( subject.key?("foo-store") ).to be_truthy
19
+ expect( subject.key?("foo-callback") ).to be_truthy
20
+ expect( subject.key?("foo-local") ).to be_truthy
21
+ end
22
+
23
+ it "returns false if key not in local_data, local_sources, or callback_sources" do
24
+ subject = described_class.new instance_double("Middleman::Application"), Middleman::CoreExtensions::Data::DATA_FILE_MATCHER
25
+
26
+ expect( subject.key?("foo-store") ).to be_falsy
27
+ expect( subject.key?("foo-callback") ).to be_falsy
28
+ expect( subject.key?("foo-local") ).to be_falsy
29
+ end
30
+
31
+ it "doesn't raise a stack error if missing the given key" do
32
+ subject = described_class.new instance_double("Middleman::Application"), Middleman::CoreExtensions::Data::DATA_FILE_MATCHER
33
+
34
+ expect{
35
+ subject.respond_to? :test
36
+ }.not_to raise_error
37
+ end
38
+
39
+ end
40
+
41
+ end
@@ -0,0 +1,96 @@
1
+ require 'spec_helper'
2
+ require 'middleman-core/util'
3
+
4
+ describe Middleman::Util do
5
+
6
+ describe "::path_match" do
7
+ it "matches a literal string" do
8
+ expect(Middleman::Util.path_match '/index.html', '/index.html').to be true
9
+ end
10
+
11
+ it "won't match a wrong string" do
12
+ expect(Middleman::Util.path_match '/foo.html', '/index.html').to be false
13
+ end
14
+
15
+ it "won't match a partial string" do
16
+ expect(Middleman::Util.path_match 'ind', '/index.html').to be false
17
+ end
18
+
19
+ it "works with a regex" do
20
+ expect(Middleman::Util.path_match /\.html$/, '/index.html').to be true
21
+ expect(Middleman::Util.path_match /\.js$/, '/index.html').to be false
22
+ end
23
+
24
+ it "works with a proc" do
25
+ matcher = lambda {|p| p.length > 5 }
26
+
27
+ expect(Middleman::Util.path_match matcher, '/index.html').to be true
28
+ expect(Middleman::Util.path_match matcher, '/i').to be false
29
+ end
30
+
31
+ it "works with globs" do
32
+ expect(Middleman::Util.path_match '/foo/*.html', '/foo/index.html').to be true
33
+ expect(Middleman::Util.path_match '/foo/*.html', '/foo/index.js').to be false
34
+ expect(Middleman::Util.path_match '/bar/*.html', '/foo/index.js').to be false
35
+
36
+ expect(Middleman::Util.path_match '/foo/*', '/foo/bar/index.html').to be true
37
+ expect(Middleman::Util.path_match '/foo/**/*', '/foo/bar/index.html').to be true
38
+ expect(Middleman::Util.path_match '/foo/**', '/foo/bar/index.html').to be true
39
+ end
40
+ end
41
+
42
+ describe "::binary?" do
43
+ %w(plain.txt unicode.txt unicode).each do |file|
44
+ it "recognizes #{file} as not binary" do
45
+ expect(Middleman::Util.binary?(File.join(File.dirname(__FILE__), "binary_spec/#{file}"))).to be false
46
+ end
47
+ end
48
+
49
+ %w(middleman.png middleman stars.svgz).each do |file|
50
+ it "recognizes #{file} as binary" do
51
+ expect(Middleman::Util.binary?(File.join(File.dirname(__FILE__), "binary_spec/#{file}"))).to be true
52
+ end
53
+ end
54
+ end
55
+
56
+ describe "::recursively_enhance" do
57
+ it "returns IndifferentHash if given one" do
58
+ input = Middleman::Util::IndifferentHash.new({test: "subject"})
59
+ subject = Middleman::Util.recursively_enhance input
60
+
61
+ expect( subject ).to be_a Middleman::Util::IndifferentHash
62
+ expect( subject.test ).to eq "subject"
63
+ end
64
+
65
+ it "returns IndifferentHash if given a hash" do
66
+ input = {test: "subject"}
67
+ subject = Middleman::Util.recursively_enhance input
68
+
69
+ expect( subject ).to be_a Middleman::Util::IndifferentHash
70
+ expect( subject.test ).to eq "subject"
71
+ end
72
+
73
+ it "returns Array with strings, or IndifferentHash, true, false" do
74
+ indifferent_hash = Middleman::Util::IndifferentHash.new({test: "subject"})
75
+ regular_hash = {regular: "hash"}
76
+ input = [ indifferent_hash, regular_hash, true, false ]
77
+ subject = Middleman::Util.recursively_enhance input
78
+
79
+ expect( subject[0] ).to be_a Middleman::Util::IndifferentHash
80
+ expect( subject[1] ).to be_a Middleman::Util::IndifferentHash
81
+ expect( subject[1].regular ).to eq "hash"
82
+ expect( subject[2] ).to eq true
83
+ expect( subject[3] ).to eq false
84
+ end
85
+
86
+ it "returns duplicated & frozen original object if not special cased" do
87
+ input = "foo"
88
+ subject = Middleman::Util.recursively_enhance input
89
+
90
+ expect( subject ).to eq input
91
+ expect( subject.object_id ).not_to eq input.object_id
92
+ expect( subject ).to be_frozen
93
+ end
94
+ end
95
+
96
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: middleman-core
3
3
  version: !ruby/object:Gem::Version
4
- version: 4.0.0.alpha.6
4
+ version: 4.0.0.beta.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Thomas Reynolds
@@ -10,7 +10,7 @@ authors:
10
10
  autorequire:
11
11
  bindir: bin
12
12
  cert_chain: []
13
- date: 2015-01-04 00:00:00.000000000 Z
13
+ date: 2015-05-02 00:00:00.000000000 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: bundler
@@ -254,14 +254,28 @@ dependencies:
254
254
  requirements:
255
255
  - - "~>"
256
256
  - !ruby/object:Gem::Version
257
- version: '0.4'
257
+ version: 0.9.0
258
258
  type: :runtime
259
259
  prerelease: false
260
260
  version_requirements: !ruby/object:Gem::Requirement
261
261
  requirements:
262
262
  - - "~>"
263
263
  - !ruby/object:Gem::Version
264
- version: '0.4'
264
+ version: 0.9.0
265
+ - !ruby/object:Gem::Dependency
266
+ name: hamster
267
+ requirement: !ruby/object:Gem::Requirement
268
+ requirements:
269
+ - - "~>"
270
+ - !ruby/object:Gem::Version
271
+ version: '1.0'
272
+ type: :runtime
273
+ prerelease: false
274
+ version_requirements: !ruby/object:Gem::Requirement
275
+ requirements:
276
+ - - "~>"
277
+ - !ruby/object:Gem::Version
278
+ version: '1.0'
265
279
  description: A static site generator. Provides dozens of templating languages (Haml,
266
280
  Sass, Compass, Slim, CoffeeScript, and more). Makes minification, compression, cache
267
281
  busting, Yaml data (and more) an easy part of your development cycle.
@@ -324,6 +338,7 @@ files:
324
338
  - features/i18n_preview.feature
325
339
  - features/ignore.feature
326
340
  - features/ignore_already_minified.feature
341
+ - features/image_srcset_paths.feature
327
342
  - features/layouts_dir.feature
328
343
  - features/liquid.feature
329
344
  - features/markdown.feature
@@ -379,6 +394,7 @@ files:
379
394
  - fixtures/asset-hash-app/source/layout.erb
380
395
  - fixtures/asset-hash-app/source/other.html.erb
381
396
  - fixtures/asset-hash-app/source/partials.html.erb
397
+ - fixtures/asset-hash-app/source/slim.html.slim
382
398
  - fixtures/asset-hash-app/source/stylesheets/_partial.sass
383
399
  - fixtures/asset-hash-app/source/stylesheets/site.css.scss
384
400
  - fixtures/asset-hash-app/source/stylesheets/uses_partials.css.sass
@@ -696,6 +712,8 @@ files:
696
712
  - fixtures/ignore-app/source/plain.html
697
713
  - fixtures/ignore-app/source/reports/another.html
698
714
  - fixtures/ignore-app/source/reports/index.html
715
+ - fixtures/image-srcset-paths-app/image-srcset-paths.html.erb
716
+ - fixtures/image-srcset-paths-app/images/blank.gif
699
717
  - fixtures/indexable-app/config.rb
700
718
  - fixtures/indexable-app/source/.htaccess
701
719
  - fixtures/indexable-app/source/.htpasswd
@@ -867,6 +885,9 @@ files:
867
885
  - fixtures/multiple-sources-app/source1/override-in-one.html.erb
868
886
  - fixtures/multiple-sources-app/source2/index2.html.erb
869
887
  - fixtures/multiple-sources-app/source2/override-in-two.html.erb
888
+ - fixtures/multiple-sources-with-duplicate-file-names-app/config.rb
889
+ - fixtures/multiple-sources-with-duplicate-file-names-app/source/index.html.erb
890
+ - fixtures/multiple-sources-with-duplicate-file-names-app/source2/index.html.erb
870
891
  - fixtures/nested-data-app/config.rb
871
892
  - fixtures/nested-data-app/data/examples/deeper/stuff.yml
872
893
  - fixtures/nested-data-app/data/examples/more.yml
@@ -991,6 +1012,7 @@ files:
991
1012
  - fixtures/stylus-preview-app/source/stylesheets/main2.css.styl
992
1013
  - fixtures/stylus-preview-app/source/stylesheets/plain.css.styl
993
1014
  - fixtures/traversal-app/config.rb
1015
+ - fixtures/traversal-app/source/.htaccess
994
1016
  - fixtures/traversal-app/source/directory-indexed.html.erb
995
1017
  - fixtures/traversal-app/source/directory-indexed/sibling.html.erb
996
1018
  - fixtures/traversal-app/source/directory-indexed/sibling2.html.erb
@@ -1107,6 +1129,7 @@ files:
1107
1129
  - lib/middleman-core.rb
1108
1130
  - lib/middleman-core/application.rb
1109
1131
  - lib/middleman-core/builder.rb
1132
+ - lib/middleman-core/cli/server.rb
1110
1133
  - lib/middleman-core/config_context.rb
1111
1134
  - lib/middleman-core/configuration.rb
1112
1135
  - lib/middleman-core/contracts.rb
@@ -1190,18 +1213,17 @@ files:
1190
1213
  - lib/middleman-core/template_context.rb
1191
1214
  - lib/middleman-core/template_renderer.rb
1192
1215
  - lib/middleman-core/util.rb
1193
- - lib/middleman-core/util/hash_with_indifferent_access.rb
1194
1216
  - lib/middleman-core/version.rb
1195
1217
  - lib/middleman/rack.rb
1196
1218
  - middleman-core.gemspec
1197
- - spec/middleman-core/binary_spec.rb
1198
1219
  - spec/middleman-core/binary_spec/middleman
1199
1220
  - spec/middleman-core/binary_spec/middleman.png
1200
1221
  - spec/middleman-core/binary_spec/plain.txt
1201
1222
  - spec/middleman-core/binary_spec/stars.svgz
1202
1223
  - spec/middleman-core/binary_spec/unicode
1203
1224
  - spec/middleman-core/binary_spec/unicode.txt
1204
- - spec/middleman-core/path_match_spec.rb
1225
+ - spec/middleman-core/core_extensions/data_spec.rb
1226
+ - spec/middleman-core/util_spec.rb
1205
1227
  - spec/spec_helper.rb
1206
1228
  homepage: http://middlemanapp.com
1207
1229
  licenses:
@@ -1223,7 +1245,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
1223
1245
  version: 1.3.1
1224
1246
  requirements: []
1225
1247
  rubyforge_project:
1226
- rubygems_version: 2.4.3
1248
+ rubygems_version: 2.4.6
1227
1249
  signing_key:
1228
1250
  specification_version: 4
1229
1251
  summary: Hand-crafted frontend development
@@ -1275,6 +1297,7 @@ test_files:
1275
1297
  - features/i18n_preview.feature
1276
1298
  - features/ignore.feature
1277
1299
  - features/ignore_already_minified.feature
1300
+ - features/image_srcset_paths.feature
1278
1301
  - features/layouts_dir.feature
1279
1302
  - features/liquid.feature
1280
1303
  - features/markdown.feature
@@ -1330,6 +1353,7 @@ test_files:
1330
1353
  - fixtures/asset-hash-app/source/layout.erb
1331
1354
  - fixtures/asset-hash-app/source/other.html.erb
1332
1355
  - fixtures/asset-hash-app/source/partials.html.erb
1356
+ - fixtures/asset-hash-app/source/slim.html.slim
1333
1357
  - fixtures/asset-hash-app/source/stylesheets/_partial.sass
1334
1358
  - fixtures/asset-hash-app/source/stylesheets/site.css.scss
1335
1359
  - fixtures/asset-hash-app/source/stylesheets/uses_partials.css.sass
@@ -1647,6 +1671,8 @@ test_files:
1647
1671
  - fixtures/ignore-app/source/plain.html
1648
1672
  - fixtures/ignore-app/source/reports/another.html
1649
1673
  - fixtures/ignore-app/source/reports/index.html
1674
+ - fixtures/image-srcset-paths-app/image-srcset-paths.html.erb
1675
+ - fixtures/image-srcset-paths-app/images/blank.gif
1650
1676
  - fixtures/indexable-app/config.rb
1651
1677
  - fixtures/indexable-app/source/.htaccess
1652
1678
  - fixtures/indexable-app/source/.htpasswd
@@ -1818,6 +1844,9 @@ test_files:
1818
1844
  - fixtures/multiple-sources-app/source1/override-in-one.html.erb
1819
1845
  - fixtures/multiple-sources-app/source2/index2.html.erb
1820
1846
  - fixtures/multiple-sources-app/source2/override-in-two.html.erb
1847
+ - fixtures/multiple-sources-with-duplicate-file-names-app/config.rb
1848
+ - fixtures/multiple-sources-with-duplicate-file-names-app/source/index.html.erb
1849
+ - fixtures/multiple-sources-with-duplicate-file-names-app/source2/index.html.erb
1821
1850
  - fixtures/nested-data-app/config.rb
1822
1851
  - fixtures/nested-data-app/data/examples/deeper/stuff.yml
1823
1852
  - fixtures/nested-data-app/data/examples/more.yml
@@ -1942,6 +1971,7 @@ test_files:
1942
1971
  - fixtures/stylus-preview-app/source/stylesheets/main2.css.styl
1943
1972
  - fixtures/stylus-preview-app/source/stylesheets/plain.css.styl
1944
1973
  - fixtures/traversal-app/config.rb
1974
+ - fixtures/traversal-app/source/.htaccess
1945
1975
  - fixtures/traversal-app/source/directory-indexed.html.erb
1946
1976
  - fixtures/traversal-app/source/directory-indexed/sibling.html.erb
1947
1977
  - fixtures/traversal-app/source/directory-indexed/sibling2.html.erb
@@ -1,103 +0,0 @@
1
- require 'middleman-core/contracts'
2
-
3
- module Middleman
4
- module Util
5
- # A hash with indifferent access and magic predicates.
6
- # Copied from Thor
7
- #
8
- # hash = Middleman::Util::HashWithIndifferentAccess.new 'foo' => 'bar', 'baz' => 'bee', 'force' => true
9
- #
10
- # hash[:foo] #=> 'bar'
11
- # hash['foo'] #=> 'bar'
12
- # hash.foo? #=> true
13
- #
14
- class HashWithIndifferentAccess < ::Hash #:nodoc:
15
- include Contracts
16
-
17
- Contract Hash => Any
18
- def initialize(hash={})
19
- super()
20
-
21
- hash.each do |key, val|
22
- self[key] = recursively_enhance(val)
23
- end
24
-
25
- freeze
26
- end
27
-
28
- def [](key)
29
- super(convert_key(key))
30
- end
31
-
32
- def []=(key, value)
33
- super(convert_key(key), value)
34
- end
35
-
36
- def delete(key)
37
- super(convert_key(key))
38
- end
39
-
40
- def values_at(*indices)
41
- indices.map { |key| self[convert_key(key)] }
42
- end
43
-
44
- def merge(other)
45
- dup.merge!(other)
46
- end
47
-
48
- def merge!(other)
49
- other.each do |key, value|
50
- self[convert_key(key)] = value
51
- end
52
- self
53
- end
54
-
55
- # Convert to a Hash with String keys.
56
- def to_hash
57
- Hash.new(default).merge!(self)
58
- end
59
-
60
- protected
61
-
62
- def convert_key(key)
63
- key.is_a?(Symbol) ? key.to_s : key
64
- end
65
-
66
- # Magic predicates. For instance:
67
- #
68
- # options.force? # => !!options['force']
69
- # options.shebang # => "/usr/lib/local/ruby"
70
- # options.test_framework?(:rspec) # => options[:test_framework] == :rspec
71
- # rubocop:disable DoubleNegation
72
- def method_missing(method, *args)
73
- method = method.to_s
74
- if method =~ /^(\w+)\?$/
75
- if args.empty?
76
- !!self[$1]
77
- else
78
- self[$1] == args.first
79
- end
80
- else
81
- self[method]
82
- end
83
- end
84
-
85
- private
86
-
87
- Contract Any => Frozen[Any]
88
- def recursively_enhance(data)
89
- if data.is_a? HashWithIndifferentAccess
90
- data
91
- elsif data.is_a? Hash
92
- self.class.new(data)
93
- elsif data.is_a? Array
94
- data.map(&method(:recursively_enhance)).freeze
95
- elsif data.frozen? || data.nil? || [::TrueClass, ::FalseClass, ::Fixnum].include?(data.class)
96
- data
97
- else
98
- data.dup.freeze
99
- end
100
- end
101
- end
102
- end
103
- end
@@ -1,15 +0,0 @@
1
- require 'middleman-core/util'
2
-
3
- describe "Middleman::Util#binary?" do
4
- %w(plain.txt unicode.txt unicode).each do |file|
5
- it "recognizes #{file} as not binary" do
6
- expect(Middleman::Util.binary?(File.join(File.dirname(__FILE__), "binary_spec/#{file}"))).to be false
7
- end
8
- end
9
-
10
- %w(middleman.png middleman stars.svgz).each do |file|
11
- it "recognizes #{file} as binary" do
12
- expect(Middleman::Util.binary?(File.join(File.dirname(__FILE__), "binary_spec/#{file}"))).to be true
13
- end
14
- end
15
- end
@@ -1,37 +0,0 @@
1
- require 'middleman-core/util'
2
-
3
- describe "Middleman::Util#path_match" do
4
- it "matches a literal string" do
5
- expect(Middleman::Util.path_match '/index.html', '/index.html').to be true
6
- end
7
-
8
- it "won't match a wrong string" do
9
- expect(Middleman::Util.path_match '/foo.html', '/index.html').to be false
10
- end
11
-
12
- it "won't match a partial string" do
13
- expect(Middleman::Util.path_match 'ind', '/index.html').to be false
14
- end
15
-
16
- it "works with a regex" do
17
- expect(Middleman::Util.path_match /\.html$/, '/index.html').to be true
18
- expect(Middleman::Util.path_match /\.js$/, '/index.html').to be false
19
- end
20
-
21
- it "works with a proc" do
22
- matcher = lambda {|p| p.length > 5 }
23
-
24
- expect(Middleman::Util.path_match matcher, '/index.html').to be true
25
- expect(Middleman::Util.path_match matcher, '/i').to be false
26
- end
27
-
28
- it "works with globs" do
29
- expect(Middleman::Util.path_match '/foo/*.html', '/foo/index.html').to be true
30
- expect(Middleman::Util.path_match '/foo/*.html', '/foo/index.js').to be false
31
- expect(Middleman::Util.path_match '/bar/*.html', '/foo/index.js').to be false
32
-
33
- expect(Middleman::Util.path_match '/foo/*', '/foo/bar/index.html').to be true
34
- expect(Middleman::Util.path_match '/foo/**/*', '/foo/bar/index.html').to be true
35
- expect(Middleman::Util.path_match '/foo/**', '/foo/bar/index.html').to be true
36
- end
37
- end