condenser 1.2 → 1.3

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 (50) hide show
  1. checksums.yaml +4 -4
  2. data/lib/condenser/asset.rb +19 -16
  3. data/lib/condenser/build_cache.rb +1 -1
  4. data/lib/condenser/context.rb +9 -25
  5. data/lib/condenser/helpers/parse_helpers.rb +1 -1
  6. data/lib/condenser/manifest.rb +3 -1
  7. data/lib/condenser/pipeline.rb +8 -3
  8. data/lib/condenser/processors/babel_processor.rb +1 -1
  9. data/lib/condenser/processors/css_media_combiner_processor.rb +81 -0
  10. data/lib/condenser/processors/js_analyzer.rb +0 -2
  11. data/lib/condenser/processors/purgecss_processor.rb +6 -4
  12. data/lib/condenser/processors/rollup_processor.rb +37 -35
  13. data/lib/condenser/resolve.rb +1 -3
  14. data/lib/condenser/templating_engine/ejs.rb +1 -1
  15. data/lib/condenser/transformers/dart_sass_transformer.rb +285 -0
  16. data/lib/condenser/transformers/jst_transformer.rb +67 -17
  17. data/lib/condenser/transformers/sass/functions.rb +133 -0
  18. data/lib/condenser/transformers/sass/importer.rb +48 -0
  19. data/lib/condenser/transformers/sass.rb +4 -0
  20. data/lib/condenser/transformers/sass_transformer.rb +124 -281
  21. data/lib/condenser/transformers/svg_transformer/base.rb +26 -0
  22. data/lib/condenser/transformers/svg_transformer/tag.rb +54 -0
  23. data/lib/condenser/transformers/svg_transformer/template.rb +151 -0
  24. data/lib/condenser/transformers/svg_transformer/template_error.rb +2 -0
  25. data/lib/condenser/transformers/svg_transformer/value.rb +13 -0
  26. data/lib/condenser/transformers/svg_transformer/var_generator.rb +10 -0
  27. data/lib/condenser/transformers/svg_transformer.rb +19 -0
  28. data/lib/condenser/version.rb +1 -1
  29. data/lib/condenser.rb +17 -5
  30. data/test/cache_test.rb +46 -2
  31. data/test/dependency_test.rb +2 -2
  32. data/test/manifest_test.rb +34 -0
  33. data/test/minifiers/terser_minifier_test.rb +0 -1
  34. data/test/minifiers/uglify_minifier_test.rb +0 -1
  35. data/test/postprocessors/css_media_combiner_test.rb +107 -0
  36. data/test/postprocessors/purgecss_test.rb +62 -0
  37. data/test/preprocessor/babel_test.rb +693 -299
  38. data/test/preprocessor/js_analyzer_test.rb +0 -2
  39. data/test/processors/rollup_test.rb +50 -20
  40. data/test/resolve_test.rb +8 -9
  41. data/test/server_test.rb +6 -1
  42. data/test/templates/ejs_test.rb +2 -11
  43. data/test/templates/erb_test.rb +0 -5
  44. data/test/test_helper.rb +3 -1
  45. data/test/transformers/dart_scss_test.rb +139 -0
  46. data/test/transformers/jst_test.rb +165 -21
  47. data/test/transformers/scss_test.rb +14 -0
  48. data/test/transformers/svg_test.rb +40 -0
  49. metadata +23 -6
  50. data/lib/condenser/transformers/sass_transformer/importer.rb +0 -50
@@ -0,0 +1,19 @@
1
+ class Condenser::SVGTransformer
2
+
3
+ autoload :Base, File.expand_path('../svg_transformer/base', __FILE__)
4
+ autoload :Tag, File.expand_path('../svg_transformer/tag', __FILE__)
5
+ autoload :Template, File.expand_path('../svg_transformer/template', __FILE__)
6
+ autoload :TemplateError, File.expand_path('../svg_transformer/template_error', __FILE__)
7
+ autoload :Value, File.expand_path('../svg_transformer/value', __FILE__)
8
+ autoload :VarGenerator, File.expand_path('../svg_transformer/var_generator', __FILE__)
9
+
10
+ def self.setup(env)
11
+ end
12
+
13
+ def self.call(environment, input)
14
+ input[:source] = Condenser::SVGTransformer::Template.new(input[:source]).to_module
15
+ end
16
+
17
+ end
18
+
19
+
@@ -1,3 +1,3 @@
1
1
  class Condenser
2
- VERSION = '1.2'
2
+ VERSION = '1.3'
3
3
  end
data/lib/condenser.rb CHANGED
@@ -19,19 +19,25 @@ class Condenser
19
19
  autoload :RollupProcessor, 'condenser/processors/rollup_processor'
20
20
  autoload :JSAnalyzer, 'condenser/processors/js_analyzer'
21
21
  autoload :PurgeCSSProcessor,'condenser/processors/purgecss_processor'
22
+ autoload :CSSMediaCombinerProcessor,'condenser/processors/css_media_combiner_processor'
22
23
  autoload :NodeProcessor, 'condenser/processors/node_processor'
23
24
  autoload :UglifyMinifier, 'condenser/minifiers/uglify_minifier'
24
25
  autoload :TerserMinifier, 'condenser/minifiers/terser_minifier'
25
26
  autoload :Erubi, 'condenser/templating_engine/erb'
27
+ autoload :Sass, 'condenser/transformers/sass'
26
28
  autoload :SassMinifier, 'condenser/minifiers/sass_minifier'
27
- autoload :SassTransformer, 'condenser/transformers/sass_transformer'
29
+ autoload :DartSassTransformer, 'condenser/transformers/dart_sass_transformer'
30
+ autoload :DartScssTransformer, 'condenser/transformers/dart_sass_transformer'
31
+ autoload :SassTransformer, 'condenser/transformers/sass_transformer'
28
32
  autoload :ScssTransformer, 'condenser/transformers/sass_transformer'
29
- autoload :EjsTemplare, 'condenser/templating_engine/ejs'
33
+ autoload :EjsTemplate, 'condenser/templating_engine/ejs'
30
34
  autoload :JstTransformer, 'condenser/transformers/jst_transformer'
35
+ autoload :SVGTransformer, 'condenser/transformers/svg_transformer'
31
36
  autoload :FileWriter, 'condenser/writers/file_writer'
32
37
  autoload :ZlibWriter, 'condenser/writers/zlib_writer'
33
38
  autoload :BrotliWriter, 'condenser/writers/brotli_writer'
34
39
  autoload :BuildCache, 'condenser/build_cache'
40
+ autoload :ParseHelpers, 'condenser/helpers/parse_helpers'
35
41
 
36
42
  def self.configure(&block)
37
43
  instance_eval(&block)
@@ -56,8 +62,8 @@ class Condenser
56
62
  configure(&block)
57
63
  elsif pipeline != false
58
64
  self.configure do
59
- # register_preprocessor 'application/javascript', Condenser::JSAnalyzer
60
- register_preprocessor 'application/javascript', Condenser::BabelProcessor
65
+ register_preprocessor 'application/javascript', Condenser::JSAnalyzer
66
+ # register_preprocessor 'application/javascript', Condenser::BabelProcessor
61
67
  register_exporter 'application/javascript', Condenser::RollupProcessor
62
68
  register_minifier 'application/javascript', Condenser::UglifyMinifier
63
69
 
@@ -132,6 +138,9 @@ Condenser.configure do
132
138
  # CSS
133
139
  register_mime_type 'text/css', extension: '.css', charset: :css
134
140
 
141
+ # PDF
142
+ register_mime_type 'application/pdf', extensions: %w(.pdf)
143
+
135
144
  # SASS
136
145
  register_mime_type 'text/sass', extensions: %w(.sass .css.sass)
137
146
  # register_transformer 'text/sass', 'text/css', SassProcessor
@@ -145,12 +154,15 @@ Condenser.configure do
145
154
 
146
155
  # EJS
147
156
  register_mime_type 'application/ejs', extensions: '.ejs', charset: :unicode
148
- register_template 'application/ejs', Condenser::EjsTemplare
157
+ register_template 'application/ejs', Condenser::EjsTemplate
149
158
 
150
159
  # JST
151
160
  register_mime_type 'application/jst', extensions: '.jst', charset: :unicode
152
161
  register_transformer 'application/jst', 'application/javascript', Condenser::JstTransformer
153
162
 
163
+ # SVG
164
+ register_transformer 'image/svg+xml', 'application/javascript', Condenser::SVGTransformer
165
+
154
166
  # Writers
155
167
  register_mime_type 'application/gzip', extensions: %w(.gz .gzip)
156
168
  register_mime_type 'application/brotli', extension: %w(.br)
data/test/cache_test.rb CHANGED
@@ -142,7 +142,7 @@ class CacheTest < ActiveSupport::TestCase
142
142
 
143
143
  end
144
144
 
145
- test 'a dependency is supurceeded by a new file' do
145
+ test 'a dependency is superceeded by a new file' do
146
146
  Dir.mkdir(File.join(@path, 'a'))
147
147
  Dir.mkdir(File.join(@path, 'b'))
148
148
  @env.clear_path
@@ -221,6 +221,21 @@ class CacheTest < ActiveSupport::TestCase
221
221
  CSS
222
222
  end
223
223
 
224
+ test '2a new dependency for a glob call is reflected in the next call' do
225
+ file "dir/a.svg", "<svg>test</svg>"
226
+ file 'test.scss', 'body { background: image-url("dir/a.svg") }'
227
+
228
+ assert_exported_file 'test.css', 'text/css', <<~CSS
229
+ body{background:url(/assets/dir/a-01a4bd3cb9faa518c5df2d2fcc8e6cd0ba24cfc3e9438dd01455ab1e59a39068.svg)}
230
+ CSS
231
+
232
+ file "dir/a.svg", "<svg>tests</svg>"
233
+
234
+ assert_exported_file 'test.css', 'text/css', <<~CSS
235
+ body{background:url(/assets/dir/a-1d7d038c7ace080963e116cbb962075a38d5e5dc68c6ff688e42d213dd432256.svg)}
236
+ CSS
237
+ end
238
+
224
239
  test 'a dependency is removed for a glob call when one of it dependencies is delted' do
225
240
  file "css/a.scss", "body { color: blue; }"
226
241
  file "css/b.scss", "body { color: green; }"
@@ -237,7 +252,7 @@ class CacheTest < ActiveSupport::TestCase
237
252
  CSS
238
253
  end
239
254
 
240
- test 'a dependency is added then changed should flush the parent' do
255
+ test 'a dependency is added then changed should flush the parent (JS)' do
241
256
  file 'a.js', "console.log('a');\n"
242
257
  file 'b.js', <<~JS
243
258
  export default function b () { console.log('b'); }
@@ -265,4 +280,33 @@ class CacheTest < ActiveSupport::TestCase
265
280
  !function(){"use strict";console.log("a"),console.log("c")}();
266
281
  JS
267
282
  end
283
+
284
+ test 'a dependency is added then changed should flush the parent (CSS)' do
285
+ file 'a.scss', "body { background: aqua; }"
286
+ file 'b.scss', <<~JS
287
+ body { background: blue; }
288
+ JS
289
+
290
+ assert_exported_file 'a.css', 'text/css', <<~JS
291
+ body{background:aqua}
292
+ JS
293
+
294
+ file 'a.scss', <<~JS
295
+ @import "b";
296
+ body { background: aqua; }
297
+ JS
298
+
299
+ assert_exported_file 'a.css', 'text/css', <<~JS
300
+ body{background:blue}body{background:aqua}
301
+ JS
302
+
303
+ file 'b.scss', <<~JS
304
+ body { background: green; }
305
+ JS
306
+
307
+ assert_exported_file 'a.css', 'text/css', <<~JS
308
+ body{background:green}body{background:aqua}
309
+ JS
310
+ end
311
+
268
312
  end
@@ -17,7 +17,7 @@ class DependencyTest < ActiveSupport::TestCase
17
17
  JS
18
18
 
19
19
  asset = @env.find('name.js')
20
- assert_equal asset.instance_variable_get(:@process_dependencies), ["models/*.js","helpers/*.js"]
20
+ assert_equal asset.instance_variable_get(:@process_dependencies).to_a, ["models/*.js","helpers/*.js"]
21
21
 
22
22
 
23
23
  assert_file 'name.js', 'application/javascript', <<~JS
@@ -54,7 +54,7 @@ class DependencyTest < ActiveSupport::TestCase
54
54
  JS
55
55
 
56
56
  asset = @env.find('name.js')
57
- assert_equal asset.instance_variable_get(:@process_dependencies), ["models/*.js","helpers/*.js"]
57
+ assert_equal asset.instance_variable_get(:@process_dependencies).to_a, ["models/*.js","helpers/*.js"]
58
58
 
59
59
 
60
60
  assert_file 'name.js', 'application/javascript', <<~JS
@@ -66,6 +66,40 @@ class ManifestTest < ActiveSupport::TestCase
66
66
  assert_equal asset.path, data['application.js']['path']
67
67
  end
68
68
 
69
+ test "compile asset dependencies includes the dependencies" do
70
+ file 'foo.svg', <<-SVG
71
+ <svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke="currentColor">
72
+ <path d="M6 18L18 6M6 6l12 12" />
73
+ </svg>
74
+ SVG
75
+
76
+ file 'test.scss', <<-SCSS
77
+ body {
78
+ background: asset-url("foo.svg");
79
+ }
80
+ SCSS
81
+
82
+ manifest = Condenser::Manifest.new(@env, File.join(@dir, 'manifest.json'))
83
+
84
+ main_digest_path = @env['test.css'].path
85
+ dep_digest_path = @env['foo.svg'].path
86
+
87
+ assert !File.exist?("#{@dir}/#{main_digest_path}")
88
+ assert !File.exist?("#{@dir}/#{dep_digest_path}")
89
+
90
+ manifest.compile('test.css')
91
+ assert File.directory?(manifest.dir)
92
+ assert File.file?(manifest.filename)
93
+
94
+ assert File.exist?("#{@dir}/manifest.json")
95
+ assert File.exist?("#{@dir}/#{main_digest_path}")
96
+ assert File.exist?("#{@dir}/#{dep_digest_path}")
97
+
98
+ data = JSON.parse(File.read(manifest.filename))
99
+ assert_equal main_digest_path, data['test.css']['path']
100
+ assert_equal dep_digest_path, data['foo.svg']['path']
101
+ end
102
+
69
103
  # TODO:
70
104
  # test "compile asset with aliased index links" do
71
105
  # manifest = Sprockets::Manifest.new(@env, File.join(@dir, 'manifest.json'))
@@ -4,7 +4,6 @@ class TerserMinifierTest < ActiveSupport::TestCase
4
4
 
5
5
  def setup
6
6
  super
7
- @env.unregister_preprocessor('application/javascript', Condenser::BabelProcessor)
8
7
  @env.unregister_exporter('application/javascript', Condenser::RollupProcessor)
9
8
  @env.register_minifier('application/javascript', Condenser::TerserMinifier)
10
9
  end
@@ -4,7 +4,6 @@ class UglifyMinifierTest < ActiveSupport::TestCase
4
4
 
5
5
  def setup
6
6
  super
7
- @env.unregister_preprocessor('application/javascript', Condenser::BabelProcessor)
8
7
  @env.unregister_exporter('application/javascript', Condenser::RollupProcessor)
9
8
  end
10
9
 
@@ -0,0 +1,107 @@
1
+ require 'test_helper'
2
+
3
+ class MediaCombinerTest < ActiveSupport::TestCase
4
+
5
+ def setup
6
+ super
7
+ @env.register_postprocessor('text/css', Condenser::CSSMediaCombinerProcessor)
8
+ @env.unregister_minifier('text/css')
9
+ end
10
+
11
+ test 'combine media queries' do
12
+ file 'main.css', <<~CSS
13
+ .test{
14
+ display: block;
15
+ }
16
+ @media only screen and (max-width: 100px) {
17
+ .test {
18
+ display: inline-block;
19
+ color: blue;
20
+ }
21
+ }
22
+ @media only screen and (max-width: 500px) {
23
+ .test {
24
+ display: inline;
25
+ }
26
+ }
27
+
28
+ .test2{
29
+ display: block;
30
+ }
31
+ @media only screen and (max-width: 100px) {
32
+ .test2 {
33
+ display: inline-block;
34
+ }
35
+ }
36
+ CSS
37
+
38
+ assert_exported_file 'main.css', 'text/css', <<~FILE
39
+ .test{
40
+ display: block;
41
+ }
42
+
43
+
44
+
45
+ .test2{
46
+ display: block;
47
+ }
48
+ @media only screen and (max-width: 100px) {
49
+ .test {
50
+ display: inline-block;
51
+ color: blue;
52
+ }
53
+
54
+ .test2 {
55
+ display: inline-block;
56
+ }
57
+ }@media only screen and (max-width: 500px) {
58
+ .test {
59
+ display: inline;
60
+ }
61
+ }
62
+ FILE
63
+ end
64
+
65
+ test 'single line css' do
66
+ file 'main.css', <<~CSS
67
+ .test{display: block;} @media only screen and (max-width: 100px) {.test {display: inline-block;}}@media only screen and (max-width: 500px) {.test {display: inline;}}.test2{display: block;}@media only screen and (max-width: 100px) {.test2 {display: inline-block;}}
68
+ CSS
69
+
70
+ assert_exported_file 'main.css', 'text/css', <<~FILE
71
+ .test{display: block;} .test2{display: block;}@media only screen and (max-width: 100px) {.test {display: inline-block;}.test2 {display: inline-block;}}@media only screen and (max-width: 500px) {.test {display: inline;}}
72
+ FILE
73
+ end
74
+
75
+
76
+ test 'keyframes' do
77
+ file 'main.css', <<~CSS
78
+ .trobber {
79
+ animation: throb 1s infinite;
80
+ }
81
+ @keyframes throb {
82
+ 0% {
83
+ opacity: 1;
84
+ }
85
+ 100%{
86
+ opacity: 0;
87
+ }
88
+ }
89
+ CSS
90
+
91
+ assert_exported_file 'main.css', 'text/css', <<~FILE
92
+ .trobber {
93
+ animation: throb 1s infinite;
94
+ }
95
+ @keyframes throb {
96
+ 0% {
97
+ opacity: 1;
98
+ }
99
+ 100%{
100
+ opacity: 0;
101
+ }
102
+ }
103
+ FILE
104
+ end
105
+
106
+
107
+ end
@@ -79,5 +79,67 @@ class PurgeCSSTest < ActiveSupport::TestCase
79
79
  }
80
80
  FILE
81
81
  end
82
+
83
+ test 'purge from html with class with /' do
84
+ file 'main.css', <<~CSS
85
+ .test{
86
+ display: block;
87
+ }
88
+ .test2-1\\/2{
89
+ display: inline;
90
+ }
91
+ CSS
92
+ file 'index.html', <<~HTML
93
+ <div class="test2-1/2"></div>
94
+ HTML
95
+
96
+ assert_exported_file 'main.css', 'text/css', <<~FILE
97
+ .test2-1\\/2{
98
+ display: inline;
99
+ }
100
+ FILE
101
+ end
102
+
103
+ test 'purge from html with nested tag' do
104
+ file 'main.css', <<~CSS
105
+ .test pre{
106
+ display: block;
107
+ }
108
+ CSS
109
+ file 'index.html', <<~HTML
110
+ <div class="test">
111
+ <pre>Test</pre>
112
+ </div>
113
+ HTML
114
+
115
+ assert_exported_file 'main.css', 'text/css', <<~FILE
116
+ .test pre{
117
+ display: block;
118
+ }
119
+ FILE
120
+ end
121
+
122
+ test 'purge from html with nested tags' do
123
+ file 'main.css', <<~CSS
124
+ code {
125
+ background: gray;
126
+ }
127
+ pre code{
128
+ background: none;
129
+ }
130
+ CSS
131
+ file 'index.html', <<~HTML
132
+ <pre><code>Test</code></pre>
133
+ HTML
134
+
135
+ assert_exported_file 'main.css', 'text/css', <<~FILE
136
+ code {
137
+ background: gray;
138
+ }
139
+ pre code{
140
+ background: none;
141
+ }
142
+ FILE
143
+ end
82
144
 
83
145
  end